반응형

String Conversions: FString to FName, FString to Int32, Float to FString


All the header files I refer to in this tutorial are found in

your UE4 install directory  / Engine / Source

you will probably want to do a search for them from this point :)

Converting FString to FNames

Say we have

FString TheString = "UE4_C++_IS_Awesome";

To convert this to an FName you do:

FName ConvertedFString = FName(*TheString);

std::string to FString

#include <string>
 
//....
 
some function
{
  std::string TestString = "Happy"; 
  FString HappyString(TestString.c_str());
}

FString to std::string

#include <string>
 
//....
FString UE4Str = "Flowers";
std::string MyStdString(TCHAR_TO_UTF8(*UE4Str));

FCString Overview

Converting FString to Numbers

The * operator on FStrings returns their TCHAR* data which is what FCString functions use.

If you cant find the function you want in FStrings (UnrealString.h) then you should check out the FCString functions (CString.h)

I show how to convert from FString to FCString below:

Say we have

FString TheString = "123.021";

FString to Integer

int32 MyShinyNewInt = FCString::Atoi(*TheString);

FString to Float

float MyShinyNewFloat = FCString::Atof(*TheString);


Note that Atoi and Atof are static functions, so you use the syntax FCString::TheFunction to call it :)


Float/Integer to FString

FString NewString = FString::FromInt(YourInt);
 
FString VeryCleanString = FString::SanitizeFloat(YourFloat);

Static functions in the UnrealString.h :)

UE4 Source Header References

CString.h
UnrealString.h
NameTypes.h

See CString.h for more details and other functions like

atoi64 (string to int64)
Atod	(string to double precision float)


For a great deal of helpful functions you will also want to look at

UnrealString.h for direct manipulation of FStrings!


For more info on FNames check out
 NameTypes.h

Enjoy!

Rama (talk)




https://wiki.unrealengine.com/String_Conversions:_FString_to_FName,_FString_to_Int32,_Float_to_FString

반응형
반응형


먼저 주의할 점은 언리얼 구조체를 만들때 구조체 이름 앞에 F를 붙여야 한다는 것에 주의!!

https://wiki.unrealengine.com/Structs,_USTRUCTS(),_They're_Awesome

Overview

Original Author: Rama (talk)

In C++, structs differ from classes only in that properties and methods defined prior to any accessibility keyword (public:protected:,private:) default to public: while in classes these default to private:. Structs are more or less artifacts of the transition from C to C++. In C, object oriented programming did not exist yet, thus structs were only used to organize data and pass that data to functions, for example, but lacked the support for methods. In C++, with the introduction of classes, this purpose became more or less deprecated. Personally I thus find it a good practice Epic is enforcing here.

Structs enable you to create custom variable types to organize your data, by relating other C++ or UE4 C++ data types to each other. The power of structs is extreme organization as well as the ability to have functions for internal data type operations. '

In UE4, structs should be used for simple data type combining and data management purposes. For complex interactions with the game world, you should make a UObject or AActor subclass instead.

Core Syntax

NOTE: Depending on your version of UE4, you'll need to replace GENERATED_BODY() with GENERATED_USTRUCT_BODY(). At least as of version 4.11, using GENERATED_USTRUCT_BODY() will result in a UHT error stating GENERATED_BODY() is expected.

//If you want this to appear in BP, make sure to use this instead
//USTRUCT(BlueprintType)
USTRUCT()
struct FJoyStruct
{
	GENERATED_BODY()
 
	//Always make USTRUCT variables into UPROPERTY()
	//    any non-UPROPERTY() struct vars are not replicated
 
	// So to simplify your life for later debugging, always use UPROPERTY()
	UPROPERTY()
	int32 SampleInt32;
 
	UPROPERTY()
	AActor* TargetActor;
 
	//Set
	void SetInt(const int32 NewValue)
	{
		SampleInt32 = NewValue;
	}
 
	//Get
	AActor* GetActor()
	{
		return TargetActor;
	}
 
	//Check
	bool ActorIsValid() const
	{
		if(!TargetActor) return false;
		return TargetActor->IsValidLowLevel();
	}
 
	//Constructor
	FJoyStruct()
	{
		//Always initialize your USTRUCT variables!
		//   exception is if you know the variable type has its own default constructor
		SampleInt32 	= 5;
		TargetActor = NULL;
	}
};


Additional Note Author: DesertEagle_PWN (talk)
Additional Note: The idea of USTRUCTS() is to declare engine data types that are in global scope and can be accessed by other classes/structs/blueprints. Because of this, it is invalid UE4 syntax to declare a struct inside of a class or other struct if using the USTRUCT() macro. Regular structs can still be utilized inside your classes and other structs; however these cannot be replicated natively and will not be available for UE4 reflective debugging or other engine systems such as Blueprints.

Examples

Example 1

You want to relate a float brightness value with a world space location FVector, both of which are interpolated using an Alpha value.

  • And you want to do this for 100 different game locations simultaneously.
  • And you want to do this process repeatedly over time!
  • You need to store the incremental interpolation values between game events.
  • AActors/UObjects are not involved (You could just subclass AActor/UObject and store the data per instance)


USTRUCT()
struct FMyInterpStruct
{
	GENERATED_BODY()
 
	UPROPERTY()
	float Brightness;
 
	UPROPERTY()
	float BrightnessGoal; //interping to
 
	UPROPERTY()
	FVector Location;
 
	UPROPERTY()
	FVector LocationGoal;
 
	UPROPERTY()
	float Alpha;
 
	void InterpInternal()
	{
		Location = FMath::Lerp<FVector>(Location,LocationGoal,Alpha);
		Brightness = FMath::Lerp<float>(Brightness,BrightnessGoal,Alpha);
	}
 
	//Brightness out is returned, FVector is returned by reference
	float Interp(const float& NewAlpha, FVector& Out)
	{
		//value received from rest of your game engine
		Alpha = NewAlpha;
 
		//Internal data structure management
		InterpInternal();
 
		//Return Values
		Out = Location;
		return Brightness;
	}
	FMyInterpStruct()
	{
		Brightness = 2; 
		BrightnessGoal = 100;
 
		Alpha = 0; 
 
		Location = FVector::ZeroVector;
		LocationGoal = FVector(0,0,200000);
	}
};

Example 2

You want to track information about particle system components that you have spawned into the world through

 UGameplayStatics::SpawnEmitterAtLocation() // returns a UParticleSystemComponent

and you want to track the lifetime of the particle and apply parameter changes from C++. You could write your own class, but if your needs are simple or you do not have project-permissions to make a subclass of UParticleSystemComponent, you can just make a USTRUCT to relate the various data types!

USTRUCT()
struct FParticleStruct
{
	GENERATED_BODY()
 
	UPROPERTY()
	UParticleSystemComponent* PSCPtr;
 
	UPROPERTY()
	float LifeTime;
 
	void SetColor()
	{
		//
	}
	FLinearColor GetCurrentColor() const
	{
		//
	}
 
	//For GC
	void Destroy()
	{
		PSCPtr = nullptr;
	}
 
	//Constructor
	FParticleStruct()
	{
		PSCPtr = NULL;
		LifeTime = -1;
	}
};

Particle Data Tracker

Now you can have an array of these USTRUCTS for each particle that you spawn!

//Particle Data Tracking Array
TArray<FParticleStruct> PSCArray;

Garbage Collection

Because all of your USTRUCT variables are UPROPERTY(), you must be careful to null them out when you are ready to destroy the particle system component.

Structs With Struct Member Variables

The struct that wants to use another struct must be defined below the struct it wants to include.

USTRUCT()
struct FFlowerStruct
{
	GENERATED_BODY()
 
	UPROPERTY()
	int32 NumPetals;
 
	UPROPERTY()
	FLinearColor Color;
 
	UPROPERTY()
	FVector Scale3D;
 
	void SetFlowerColor(const FLinearColor& NewColor)
	{
		Color = NewColor;
	}
 
	FFlowerStruct()
	{
		NumPetals 	= 5;
		Scale3D 		= FVector(1,1,1);
		Color 			= FLinearColor(1,0,0,1);
	}
};
 
USTRUCT()
struct FIslandStruct
{
	GENERATED_BODY()
 
	UPROPERTY()
	int32 Type;
 
	UPROPERTY()
	TArray<FVector> StarLocations;
 
	UPROPERTY()
	float RainAlpha;
 
	//Dynamic Array of Flower Custom USTRUCT()
	UPROPERTY()
	TArray<FFlowerStruct> FlowersOnThisIsland;
 
	void SetRainAlpha(const float& NewAlpha) 
	{
		RainAlpha = NewAlpha;
	}
 
	int32 GetStarCount() const
	{
		return StarLocations.Num();
	}
	FIslandStruct()
	{
		Type = 0;
		Percent = 1;
	}
};

Struct Assignment

My personal favorite thing about structs is that unlike UObject or AActor classes, which must be utilized via pointers (AActor*) you can directly copy the entire contents of a USTRUCT to another USTRUCT of the same type with a single line of assignment!

FFlowerStruct ExistingFlower;
 
// ... create ExistingFlower here
 
FFlowerStruct NewFlower;
NewFlower = ExistingFlower;

Caveat: Deep Copy

A misconception of the original author is probably that Epic created code in the GENERATED_BODY() macro that would deep-copy a struct upon assigning it to another. In reality, struct assignment has always been a shallow copy in native C. Thus if you were to assign one struct to another like so:

USTRUCT()
struct FMyStruct {
    int32* MyIntArray;
};
 
FMyStruct MyFirstStruct, MySecondStruct;
 
// Create the integer array on the first struct
MyFirstStruct.MyIntArray = new int32[10];
for( int i = 0; i < 10; ++i ) {
  MyFirstStruct.MyIntArray[i] = i;
}
 
GEngine->AddOnScreenMessage(-1, 10.f, FColor::Blue, FString::FromInt(MyFirstStruct.MyIntArray[4]));
 
// Assign the first struct to the second struct, i.e. create a shallow copy
MySecondStruct.MyIntArray[4] = 6;
 
GEngine->AddOnScreenMessage(-1, 10.f, FColor::Blue, FString::Printf(TEXT("%d %d"), MyFirstStruct.MyIntArray[4], MySecondStruct.MyIntArray[4]));

On screen the output will be

 4
 6 6

instead of the expected

 4
 4 6

This is because the data stored in MyStruct::MyIntArray is not actually stored inside of MyStruct. The new keyword creates the data somewhere in RAM and we simply store a pointer there. The address the pointer stores is copied over to MySecondStruct, but it still points to the same data. In fact, it would be counterproductive to remove this functionality since there are cases where you want exactly that. Additionally the Unreal Property System does not support non-UObject pointers, which is why MyIntArray is not marked with UPROPERTY().

However, copying arrays of integers (e.g. int32[10] instead of int32*) means the data is stored directly inside the struct and as such "deep copied". However, if you store a pointer to a UObject, this object is NOT deep copied! Once again only the pointer is copied and the original UObject left unchanged. Which is good because otherwise you might manipulate the wrong instance thinking you only had one to begin with leaving the original UObject unaffected, thus resembling a very nerve-wrecking and very difficult to track down bug!


이 부분이 핀 분할/ 재결합 부분으로

UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Flower Struct") 이 한줄이 중요함

Automatic Make/Break in BP

Marking the USTRUCT as BlueprintType and adding EditAnywhere, BlueprintReadWrite, Category = "Your Category" to USTRUCT properties causes UE4 to automatically create Make and Break Blueprint functions, allowing to construct or extract data from the custom USTRUCT.

Special thanks to Community member Iniside for pointing this out. :)

USTRUCT(BlueprintType)
struct FFlowerStruct
{
	GENERATED_BODY()
 
	UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Flower Struct")
	int32 NumPetals;
 
	UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Flower Struct")
	FLinearColor Color;
 
	UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Flower Struct")
	FVector Scale3D;
};

CustomUStructMakeBreak.jpg

Replication




 Remember that only UPROPERTY() variables of USTRUCTS() are considered for replication!



So if your USTRUCT is not replicating properly, the first thing you should check is that every member is at least UPROPERTY()! The struct does not have be a BlueprintType, it just needs UPROPERTY() above all properties that you want replicated.

Related Links

UStruct data member memory management

Thank You Epic for USTRUCTS()

I love USTRUCTS(), thank you Epic!

반응형
반응형

언리얼4 블루프린트에서 short 그리고 uint64 같은 바이트를 지원하지 않는데 


short 이야 int 로 친다 하더래도, 8바이트 짜리는?? -> 이건 Fstring 으로 변환해 사용한다




Unreal Engine 4 - Converting uint64_t to FString


http://blog.vkarlsson.com/

In our current Game Jam we wanted BIG numbers for our score, so to make sure that the code can handle BIG numbers I wanted to implement the score as a unsigned long long int.

Unreal Engine 4 doesn’t support uint64_t to be converted into FString by default so I had to find a solution.

The solution was a combination of C++ string-stream strings and of course FString.

Below is the conversion code:

FString AGameHUD::GetScore()
{
  std::ostringstream ss;
  std::string s;
  s = (ss << Score).str();
  FString f(s.c_str());
  return f;
}


반응형
반응형

c++ 코드에서 함소 호출 시  인자와 같이 넘길 수 있는 방법은


함수명뒤에 인자를 같이 붙여주면 된다 아래처럼 단위 함수로 만들면 유용


https://answers.unrealengine.com/questions/116529/call-blueprint-functions-from-c.html?sort=oldest



Another bit of useful code....

  1. char funcCallBuf[1024];
  2. void UTDLSurvivorFastCache::CallActorFunc(AActor * c, FString funcName)
  3. {
  4. FOutputDeviceNull ar;
  5. c->CallFunctionByNameWithArguments(*funcName, ar, NULL, true);
  6. }
  7. void UTDLSurvivorFastCache::CallActorFuncIntParam(AActor * c, FString funcName, int32 f)
  8. {
  9. _snprintf(funcCallBuf, sizeof(funcCallBuf), "%s %d", *funcName, f);
  10. FOutputDeviceNull ar;
  11. c->CallFunctionByNameWithArguments(ANSI_TO_TCHAR(funcCallBuf), ar, NULL, true);
  12. }
  13. void UTDLSurvivorFastCache::CallActorFuncFloatParam(AActor * c, FString funcName, float f)
  14. {
  15. _snprintf(funcCallBuf, sizeof(funcCallBuf), "%s %f", *funcName, f);
  16. FOutputDeviceNull ar;
  17. c->CallFunctionByNameWithArguments(ANSI_TO_TCHAR(funcCallBuf), ar, NULL, true);
  18. }
  19. void UTDLSurvivorFastCache::CallActorFuncFloatIntParam(AActor * c, FString funcName, float f, int32 n)
  20. {
  21. _snprintf(funcCallBuf, sizeof(funcCallBuf), "%s %f %d", *funcName, f, n);
  22. FOutputDeviceNull ar;
  23. c->CallFunctionByNameWithArguments(ANSI_TO_TCHAR(funcCallBuf), ar, NULL, true);
  24. }

xlar8or gravatar image xlar8or Dec 22 '15 at 10:33 PM Newest

Is there a way to do this for a AActor parameter?



C++에서 블루프린트 함수 호출하기 .1


http://3dmpengines.tistory.com/1615

반응형
반응형


Ok, got this working so here is an example....

I want to call a blueprint function from C++.

So first I make a blueprint function called CallFunctionTest. (In our game, and we call a player a "Survivor".) It just prints "Survivor Call Function Test" in pink on the console.

Then I have a static blueprint set of functions like this...

The header file is

  1. #include "Kismet/BlueprintFunctionLibrary.h"
  2. #include "TDLSurvivorFastCache.generated.h"
  3. /**
  4. *
  5. */
  6. UCLASS()
  7. class TDL_API UTDLSurvivorFastCache : public UBlueprintFunctionLibrary
  8. {
  9. GENERATED_UCLASS_BODY()
  10. public:
  11. UFUNCTION(BlueprintCallable, Category = TDLSurvivorCache)
  12. static void TestCPPCallToBP(AActor * c);
  13. };

and the cpp file is...

  1. #include "tdl.h"
  2. #include "ConsoleManager.h"
  3. #include "TDLSurvivorFastCache.h"
  4. UTDLSurvivorFastCache::UTDLSurvivorFastCache(const class FObjectInitializer & PCIP)
  5. : Super(PCIP)
  6. {
  7. UE_LOG(TDLLog, Log, TEXT("UTDLSurvivorFastCache"));
  8. }
  9. void UTDLSurvivorFastCache::TestCPPCallToBP(AActor * c)
  10. {
  11. FOutputDeviceNull ar;
  12. c->CallFunctionByNameWithArguments(TEXT("CallFunctionTest"), ar, NULL, true);
  13. }

Then we call the test function from our SurvivorBP blueprint and it calls the function on the SurvivorBP.

Here are the blueprints

alt text

alt text


https://answers.unrealengine.com/questions/116529/call-blueprint-functions-from-c.html?sort=oldest


반응형
반응형

Blueprints, Empower Your Entire Team With BlueprintImplementableEvent

Overview

Original Author: Rama (talk)

Dear Community,

Here is perhaps the most powerful thing you can do as a c++ programmer for blueprint programmers!

So you've created your awesome new amazing C++ system,

but how do you tell the blueprint world when critical events occur in your C++ system?

You need to not only be able to have blueprint programmers call functions that use your C++ system,

you need to be able to spontaneously provide info to blueprint graph system, based on Run-Time events.

This is where BlueprintImplementableEvents come into play!

Providing Blueprints With Data And Critical Timings

Using the BlueprintImplementableEvent you can not only tell blueprints when a critical game event has occurred that your awesome C++ system is tracking / creating,

you can also send variable data to blueprints!

Example code below!

PlayerController.h

.h

/** Player's Health is Currently Above 50! Returns 
player's exact current health for convenience. This 
function runs every tick that the player's health 
is high enough! Play healthy sounds here. */
UFUNCTION(BlueprintImplementableEvent, meta=(FriendlyName = "Player Health ~ Player Is Healthy Tick"))
void PlayerIsHealthyTick(float CurrentHealth);

.cpp

void AYourPlayerController::PlayerTick(float DeltaTime)
{
	Super::PlayerTick(DeltaTime);
 
	//========================
	// 	BP Interface
	if(Health >= 50) 
	{
		this->PlayerIsHealthyTick(Health);
	}
	//========================
}

CPPBPEvent.jpg

This

 this->PlayerIsHealthyTick(Health);

I personally use this-> to tell myself I am not actually calling a C++ function, but am sending info to BP.

You could exclude the use of this->

Tick Function

Note that the sample code is sending an event to blueprints every tick!

You can call BlueprintImplementableEvent's any way you want,

but I used this example to show a constant interfacing from c++ to blueprint graphs.

Sending Data to Blueprints From C++

Notice how the player's current health is being sent to blueprints as a function parameter!

You can pass any data you want from C++ to blueprints this way!

Calling a BlueprintImplementableEvent in Blueprints

Make sure to include BlueprintCallable if you want to also call your event in Blueprints!

UFUNCTION(Category = "Player Health", BlueprintImplementableEvent, BlueprintCallable)
void PlayerIsHealthyTick(float CurrentHealth);

4.8 Standard, Non Virtual

As of 4.8 BlueprintImplementableEvents should not be made virtual!

From the 4.8 Engine upgrade notes:

 Removed "virtual" keyword from several engine-level BlueprintImplementableEvents 
 to conform to the new "BlueprintImplementableEvents should not be virtual" standard.

Debugging BlueprintImplementableEvent

Void Return Value

If you are having trouble getting a BlueprintImplementableEvent to show up in the blueprint graph, try making sure that your return type is void.

If you do have a return type, your BP implementable event will show up in the left panel and you can right click to implement it.

Do Not Pass by Non-Const Reference

Also, I dont recommend trying to pass data to blueprints using non-const reference.

either use const reference or no reference at all.

/** Player's Health is Currently Above 50! Returns player's exact current health for convenience. This function runs every tick that the player's health is high enough! Play healthy sounds here. */
UFUNCTION(BlueprintImplementableEvent, meta=(FriendlyName = "Player Health ~ Player Is Healthy Tick"))
void PlayerIsHealthyTick(float CurrentHealth);
/** Player's Health is Currently Above 50! Returns player's exact current health for convenience. This function runs every tick that the player's health is high enough! Play healthy sounds here. */
UFUNCTION(BlueprintImplementableEvent, meta=(FriendlyName = "Player Health ~ Player Is Healthy Tick"))
void PlayerIsHealthyTick(const float& CurrentHealth);

C++ to BP Interface

I am using the term interface loosely here, to describe how it is that you as the C++ programmer of an awesome new game mechanic can give Blueprint users all the info they need about what your C++ system is doing!

You can do all the core calculations in C++, and just send blueprint graphs the results!

Blueprints For More Than Prototyping

Using BlueprintImplementableEvent's I can now show you that blueprints are amazing for far more than just prototyping game logic that should then be re-written in C++.

Using BlueprintImplementableEvent's, you can actually build a complex low-level c++ system,

and then provide the blueprint graphs with all the critical access points and information needed,

so that blueprints can fully extend and utilize the core C++ system!

Use Blueprints & BlueprintImplementableEvent to Empower Your Entire Team

In this way, you as a C++ programmer can empower your entire team to access, utilize, and extend a core C++ system in blueprints!

This is my favorite thing about the synergy of C++ with Blueprints!

You can write the core system in C++, and then give all of its power and new creativity to the blueprint programmers to take in all sorts of new directions!

Enjoy!


반응형
반응형

Delegate UE4


https://docs.unrealengine.com/latest/KOR/Programming/UnrealArchitecture/Delegates/index.html


델리게이트로 C++ 오브젝트 상의 멤버 함수 호출을 일반적이고 유형적으로 안전한 방식으로 할 수 있습니다. 델리게이트를 사용하여 임의 오브젝트의 멤버 함수에 동적으로 바인딩시킬 수 있으며, 그런 다음 그 오브젝트에서 함수를 호출할 수 있습니다. 호출하는 곳에서 오브젝트의 유형을 몰라도 말이지요.

델리게이트 오브젝트는 복사해도 완벽히 안전합니다. 델리게이트는 값으로 전달 가능하나 보통 추천할 만 하지는 않는데, heap 에 메모리를 할당해야 하기 때문입니다. 가급적이면 델리게이트는 항상 참조 전달해야 합니다.

델리게이트는 싱글-캐스트(형 변환)와 멀티-캐스트 모두 지원되며, 디스크에 안전하게 Serialize 시킬 수 있는 "다이내믹" 델리게이트도 물론입니다.

델리게이트 선언하기

델리게이트의 선언은 제공되어 있는 선언 매크로 중 하나를 사용하여 이루어집니다. 사용되는 매크로는 델리게이트에 바인딩되는 함수의 시그너처에 따라 결정됩니다. 시스템에서는 델리게이트 유형을 선언해 낼 수 있는 범용 함수 시그너처의 다양한 조합을 미리 정의, 이를 통해 반환값과 파라미터에 대한 유형 이름을 필요한 대로 채워넣습니다. 현재 다음 항목들의 어떠한 조합에 대해서도 델리게이트 시그너처가 지원됩니다:

  • 값을 반환하는 함수

  • "페이로드"(payload, 유상) 변수 4 개 까지

  • 함수 파라미터 8 개 까지

  • 'const' 로 선언된 함수

이 표에서 델리게이트 선언에 사용할 매크로를 찾을 수 있습니다.

함수 시그너처선언 매크로
void Function()DECLARE_DELEGATE( DelegateName )
void Function( <Param1> )DECLARE_DELEGATE_OneParam( DelegateName, Param1Type )
void Function( <Param1>, <Param2> )DECLARE_DELEGATE_TwoParams( DelegateName, Param1Type, Param2Type )
void Function( <Param1>, <Param2>, ... )DECLARE_DELEGATE_<Num>Params( DelegateName, Param1Type, Param2Type, ... )
<RetVal> Function()DECLARE_DELEGATE_RetVal( RetValType, DelegateName )
<RetVal> Function( <Param1> )DECLARE_DELEGATE_RetVal_OneParam( RetValType, DelegateName, Param1Type )
<RetVal> Function( <Param1>, <Param2> )DECLARE_DELEGATE_RetVal_TwoParams( RetValType, DelegateName, Param1Type, Param2Type )
<RetVal> Function( <Param1>, <Param2>, ... )DECLARE_DELEGATE_RetVal_<Num>Params( RetValType, DelegateName, Param1Type, Param2Type, ... )

멀티-캐스트, 다이내믹, 래핑된(wrapped) 델리게이트에 대한 변종 매크로도 제공됩니다:

  • DECLARE_MULTICAST_DELEGATE...

  • DECLARE_DYNAMIC_DELEGATE...

  • DECLARE_DYNAMIC_MULTICAST_DELEGATE...

  • DECLARE_DYNAMIC_DELEGATE...

  • DECLARE_DYNAMIC_MULTICAST_DELEGATE...

델리게이트 시그너처 선언은 글로벌 영역에, 네임스페이스 안이나 심지어 (함수 본문은 제외한) 클래스 선언부 안에까지도 존재 가능합니다.

이러한 델리게이트 유형 선언에 있어서의 자세한 정보는 다이내믹 델리게이트 , 멀티캐스트 델리게이트 페이지를 참고해 주시기 바랍니다.

델리게이트 바인딩하기

델리게이트 시스템은 특정 유형의 오브젝트를 이해하고 있으며, 이러한 오브젝트를 사용할 때는 추가적으로 사용할 수 있는 기능이 있습니다. UObject 나 공유 포인터 클래스 멤버에 델리게이트를 바인딩하는 경우, 델리게이트 시스템은 그 오브젝트에 대한 약한 레퍼런스를 유지할 수 있어, 델리게이트 치하에서 오브젝트가 소멸된 경우 IsBound() 나 ExecuteIfBound() 함수를 호출하여 처리해 줄 수 있습니다. 참고로 여러가지 지원되는 오브젝트 유형에 대해서는 특수한 바인딩 문법이 사용됩니다.

함수설명
Bind()기존 델리게이트 오브젝트에 바인딩합니다.
BindStatic()raw C++ 포인터 글로벌 함수 델리게이트를 바인딩합니다.
BindRaw()날(raw) C++ 포인터 델리게이트에 바인딩합니다. 날 포인터는 어떠한 종류의 레퍼런스도 사용하지 않아, 만약 오브젝트가 델리게이트 치하에서 삭제된 경우 호출하기가 안전하지 않을 수도 있습니다. Execute() 호출시에는 조심하세요!
BindSP()공유 포인터-기반 멤버 함수 델리게이트에 바인딩합니다. 공유 포인터 델리게이트는 오브젝트로의 약한 레퍼런스를 유지합니다. ExecuteIfBound() 로 호출할 수 있습니다.
BindUObject()UObject 기반 멤버 함수 델리게이트를 바인딩합니다. UObject 델리게이트는 오브젝트로의 약한 레퍼런스를 유지합니다.ExecuteIfBound() 로 호출할 수 있습니다.
UnBind()이 델리게이트 바인딩을 해제합니다.

이 함수들의 변종, 인수, 구현을 확인하시려면 (..\UE4\Engine\Source\Runtime\Core\Public\Templates\ 에 있는)DelegateSignatureImpl.inl 파일을 확인해 주시기 바랍니다.

페이로드 데이터

델리게이트에 바인딩할 때, 페이로드 데이터를 같이 전해줄 수 있습니다. 페이로드 데이터란 바인딩된 함수를 불러낼(invoke) 때 직접 전해지는 임의의 변수를 말합니다. 바인딩 시간에 델리게이트 자체적으로 파라미터를 보관할 수 있게 되니 매우 유용합니다. ("다이내믹"을 제외한) 모든 델리게이트 유형은 페이로드 변수를 자동으로 지원합니다. 이 예제는 커스텀 변수 둘, 즉 bool 과 int32 를 델리게이트에 전달합니다. 그런 다음 델리게이트를 불러낼 때 이 파라미터가 바인딩된 함수에 전달됩니다. 여분의 변수 인수는 반드시 델리게이트 유형 파라미터 인수 이후에 받아야 합니다.

MyDelegate.BindRaw( &MyFunction, true, 20 );

델리게이트 실행하기

델리게이트에 바인딩된 함수는 델리게이트의 Execute() 함수를 호출하여 실행됩니다. 델리게이트를 실행하기 전 "바인딩" 되었는지 반드시 확인해야 합니다. 이는 코드 안전성을 도모하기 위함인데, 초기화되지 않은 상태로 접근이 가능한 반환값과 출력 파라미터가 델리게이트에 있을 수 있기 때문입니다. 바인딩되지 않은 델리게이트를 실행시키면 일부 인스턴스에서 메모리에 낙서를 해버릴 수가 있습니다. 델리게이트가 실행해도 안전한 지는 IsBound() 를 호출하여 검사해 볼 수 있습니다. 또한 반환값이 없는 델리게이트에 대해서는ExecuteIfBound() 를 호출할 수 있으나, 출력 파라미터는 초기화되지 않을 수 있다는 점 주의하시기 바랍니다.

실행 함수설명
Execute()
ExecuteIfBound()
IsBound()

멀티-캐스트 델리게이트 관련 자세한 내용은 멀티캐스트 델리게이트 페이지를 확인하시기 바랍니다.

사용 예제

아무데서나 호출했으면 하는 메소드를 가진 클래스가 있다고 쳐 봅시다:

class FLogWriter
{
    void WriteToLog( FString );
};

WriteToLog 함수를 호출하려면, 해당 함수의 시그너처에 맞는 델리게이트 유형을 생성해야 합니다. 그러기 위해서는 먼저 아래 매크로 중 하나를 사용하여 델리게이트를 선언해야 합니다. 여기 예제에서는 단순한 델리게이트 유형입니다:

DECLARE_DELEGATE_OneParam( FStringDelegate, FString );

이는 'FStringDelegate' 라는 델리게이트 유형을 생성하며, 'FString' 유형 파라미터를 하나 받습니다.

클래스에서 이 'FStringDelegate' 를 어떻게 사용하는가, 예제는 이렇습니다:

class FMyClass
{
    FStringDelegate WriteToLogDelegate;
};

이렇게 하여 위 클래스의 임의 클래스 안에 있는 메소드로의 포인터를 담을 수 있습니다. 위 클래스가 이 델리게이트에 대해 아는 것이라고는, 함수 시그너처 뿐입니다.

이제 델리게이트 할당을 위해, 단순히 델리게이트 클래스의 인스턴스를 생성하고, 그 메소드를 소유하는 클래스와 함께 템플릿 파라미터로 전해줍니다. 자기 오브젝트의 인스턴스와 그 메소드의 실제 함수 주소 역시도 전해줘야 합니다. 그래서 여기서는 우리 'FLogWriter' 클래스의 인스턴스를 생성한 다음, 그 오브젝트 인스턴스의 'WriteToLog' 메소드에 대한 델리게이트를 생성하겠습니다.

FSharedRef< FLogWriter > LogWriter( new FLogWriter() );

WriteToLogDelegate.BindSP( LogWriter, &FLogWriter::WriteToLog );

이렇게 하여 클래스의 메소드에 델리게이트를 동적으로 바인딩하였습니다! 차암 쉽죠?

BindSP 의 SP 부분은 shared pointer, 공유 포인터를 뜻하는데, 공유 포인터에 소유된 오브젝트에 바인딩하고 있기 때문입니다. BindRaw(), BindUObject() 처럼 다양한 오브젝트 유형 버전도 있습니다.

이제 'FLogWriter' 클래스에 대해 아무것도 모를지라도 FMyClass 를 통해 'WriteToLog' 메소드를 호출할 수 있습니다! 자신의 델리게이트를 호출하려면, 그냥 'Execute()' 메소드를 사용하면 됩니다:

WriteToLogDelegate.Execute( TEXT( "델리게이트 쥑이네!" ) );

델리게이트에 함수를 바인딩하기 전 Execute() 를 호출하면 assert 가 발동됩니다. 그런 경우를 피하기 위해 대부분 이렇게 하는 것이 좋습니다:

WriteToLogDelegate.ExecuteIfBound( TEXT( "함수가 바인딩되었을 때만 실행!" ) );




반응형
반응형

Remarks

GameInstance: high-level manager object for an instance of the running game. Spawned at game creation and not destroyed until game instance is shut down. Running as a standalone game, there will be one of these. Running in PIE (play-in-editor) will generate one of these per PIE instance.



가비지 컬렉터에의해 제거 되지 않도록 플래그 값을 세팅해줘야한다



반응형
반응형

UGameInstance

  • SHARE:

Remarks

GameInstance: high-level manager object for an instance of the running game. Spawned at game creation 

and not destroyed until game instance is shut down. Running as a standalone game, 

there will be one of these. Running in PIE (play-in-editor) will generate one of these per PIE instance.


https://docs.unrealengine.com/latest/INT/API/Runtime/Engine/Engine/UGameInstance/index.html





Thread: Game Instance VS Singleton

  1. #1
    0
    Infiltrator
    Join Date
    Jul 2014
    Posts
    14

    Game Instance VS Singleton

    The recently released UE 4.4 introduced the new UGameInstance class. From what I understand you can have a single global instance of UGameInstance per game and it stays even between level transitions. But I wonder: what are the main differences between a UGameInstance and a Singleton object (which was already available in earlier versions of UE4)? Do they have any advantages over one another or can do anything the other type can't? When should I use which type?
    Quick reply to this messageReply   Reply With QuoteReply With Quote   Multi-Quote This Message     
  2. #2
    0
    Unreal Engine Developer
    Join Date
    Mar 2014
    Posts
    294
    Frankly, GameSingleton was a bit of a hack put in by one of our game teams to deal with the fact that something like GameINstance didn't exist. I'd definitely recommend not using it going forward.

    In a standalone game the GameInstance and a Singleton (that is allocated at startup and cleaned up at shutdown) will have very similar lifespans, however, in the editor, GameInstance will exist just while a Play in Editor (PIE) session is running and there will be one for each PIE session. Game Singleton will exist for the entire duration of the editor and need to be cleaned up or managed each time you start or end a PIE session and if you are using the multiplayer PIE feature (where you can have multiple networked PIE windows within the editor) there is only one Singleton that is shared between them.


https://forums.unrealengine.com/showthread.php?29765-Game-Instance-VS-Singleton

반응형
반응형
  1. #1
    0
    Samaritan
    Join Date
    Jul 2014
    Posts
    130

    Question BeginPlay VS Constructor?

    I have been trying to spawn a certain object when the game starts and have been using constructor to do so, but nothing is happening. DebugMessages I surrounded it with are neither firing. Is there some crucial difference between BeginPlay and contructor?
    Quick reply to this messageReply   Reply With QuoteReply With Quote   Multi-Quote This Message     
  2. #2
    0
    Champion
    Join Date
    Mar 2014
    Posts
    627
    This is due to that when the constructor is called the Actor or world is potentaly not loaded.
    You can use BeginPlay if the actor is placed in the world, or PostInitelize methods to do this.






https://forums.unrealengine.com/showthread.php?27461-BeginPlay-VS-Constructor

반응형
반응형



http://cafe.naver.com/unrealenginekr/735

1. [프로젝트명].Build.cs
사용할 모듈 이름 추가
--> 
PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", "Networking", "Sockets" });

2. [클래스명].h
모듈 헤더 추가
--> 
#include "Engine.h"
#include "Networking.h"
#include "Sockets.h"
#include "SocketSubsystem.h"

BP 에서 사용한다면 노출시킬 함수에 매크로 설정
-->  
UFUNCTION(BlueprintCallable, Category = Socket)
 void ConnectToServer();

3. [클래스명].cpp
코드 구현
-->
 FSocket* Socket = ISocketSubsystem::Get(PLATFORM_SOCKETSUBSYSTEM)->CreateSocket(NAME_Stream, TEXT("default"), false);

 FString address = TEXT("127.0.0.1");
 int32 port = 8989;
 FIPv4Address ip;
 FIPv4Address::Parse(address, ip);

 TSharedRef<FInternetAddr> addr = ISocketSubsystem::Get(PLATFORM_SOCKETSUBSYSTEM)->CreateInternetAddr();
 addr->SetIp(ip.GetValue());
 addr->SetPort(port);

 GEngine->AddOnScreenDebugMessage(-1, 5.f, FColor::Red, FString::Printf(TEXT("Trying to connect.")));

 bool connected = Socket->Connect(*addr);


반응형
반응형

마티네를 플레이했는 데도 불구하고 이벤트가 발동 되지 않았던 현상이 있었는데


이벤트 트렉 아래 빨간 화살 표 보면 두개 화살표 버튼을 활성/비활성화 할 수 있는데 활성화 되어 있어야지만

정방향/역방향 이벤트가 발동 할 수 있음.... ㅡ.ㅡ;; ㅋㅋ






참고 : http://docs.unrealengine.com/latest/KOR/Engine/Matinee/TrackReference/index.html

반응형
반응형




You have to specify which Object types you are looking for when you call the function:

Signature:

  1. bool GetHitResultUnderCursorForObjects ( const TArray< TEnumAsByte< EObjectTypeQuery > > & ObjectTypes, bool bTraceComplex, FHitResult & HitResult )
  2.  

Implementation

  1. //Init the Array
  2. TArray< TEnumAsByte< EObjectTypeQuery > > ObjectTypes;
  3. ObjectTypes.Add(EObjectTypeQuery::ObjectTypeQuery1);
  4. ObjectTypes.Add(EObjectTypeQuery::ObjectTypeQuery2);
  5. //... any other types you want
  6. FHitResult Hit;
  7. bool bHitOccurred = GetHitResultUnderCursorForObjects(ObjectTypes,true,Hit);
  8. if(bHitOccurred)
  9. {
  10. //utilize Hit.GetActor() to know who was hit
  11. }
  12.  
  13.  

The enum is not particularly C++ friendly, here's the whole enum, probably better to use this particular function in BP or write your own version in C++.

EngineTypes.h

  1. UENUM(BlueprintType)
  2. enum EObjectTypeQuery
  3. {
  4. ObjectTypeQuery1 UMETA(Hidden),
  5. ObjectTypeQuery2 UMETA(Hidden),
  6. ObjectTypeQuery3 UMETA(Hidden),
  7. ObjectTypeQuery4 UMETA(Hidden),
  8. ObjectTypeQuery5 UMETA(Hidden),
  9. ObjectTypeQuery6 UMETA(Hidden),
  10. ObjectTypeQuery7 UMETA(Hidden),
  11. ObjectTypeQuery8 UMETA(Hidden),
  12. ObjectTypeQuery9 UMETA(Hidden),
  13. ObjectTypeQuery10 UMETA(Hidden),
  14. ObjectTypeQuery11 UMETA(Hidden),
  15. ObjectTypeQuery12 UMETA(Hidden),
  16. ObjectTypeQuery13 UMETA(Hidden),
  17. ObjectTypeQuery14 UMETA(Hidden),
  18. ObjectTypeQuery15 UMETA(Hidden),
  19. ObjectTypeQuery16 UMETA(Hidden),
  20. ObjectTypeQuery17 UMETA(Hidden),
  21. ObjectTypeQuery18 UMETA(Hidden),
  22. ObjectTypeQuery19 UMETA(Hidden),
  23. ObjectTypeQuery20 UMETA(Hidden),
  24. ObjectTypeQuery21 UMETA(Hidden),
  25. ObjectTypeQuery22 UMETA(Hidden),
  26. ObjectTypeQuery23 UMETA(Hidden),
  27. ObjectTypeQuery24 UMETA(Hidden),
  28. ObjectTypeQuery25 UMETA(Hidden),
  29. ObjectTypeQuery26 UMETA(Hidden),
  30. ObjectTypeQuery27 UMETA(Hidden),
  31. ObjectTypeQuery28 UMETA(Hidden),
  32. ObjectTypeQuery29 UMETA(Hidden),
  33. ObjectTypeQuery30 UMETA(Hidden),
  34. ObjectTypeQuery31 UMETA(Hidden),
  35. ObjectTypeQuery32 UMETA(Hidden),
  36. ObjectTypeQuery_MAX UMETA(Hidden)
  37. };



https://answers.unrealengine.com/questions/252257/gethitresultundercursorforobjects-array.html


반응형
반응형

Event End Play

This event is executed when the Actor ceases to be in the World.



Event End Play

액터가 더이상 월드에 존재하지 않게 되면 실행되는 이벤트입니다.





Event Destroyed

액터가 Destroy (소멸)되었을 때 실행되는 이벤트입니다.


Destroyed Event 는 앞으로 폐기될 예정입니다. Destroyed 함수 내 함수성은 EndPlay 함수로 통합되었습니다.



https://docs.unrealengine.com/latest/KOR/Engine/Blueprints/UserGuide/Events/index.html


반응형
반응형

Hi,

It's much easier to manage level streaming in blueprints instead of C++.
Take a look at GetStreamingLevel BP node. It gives you full control over level streaming.

Name:  levelstreaming_1.png
Views: 1840
Size:  55.4 KB

Name:  levelstreaming_2.png
Views: 1843
Size:  59.8 KB




Thread: Level streaming with C++

https://forums.unrealengine.com/showthread.php?26581-Level-streaming-with-C
  1. #1
    0
    Supporter
    Join Date
    Aug 2014
    Posts
    4

     [SOLVED] Level streaming with C++

    Hi everyone ,

    I have a short question (or long).

    I have now searched for hours and tested some code but I can't find information about correct level streaming with C++.

    What I want to do is:

    I have 2 maps ("map1", "map2", "this" is a class derived from"AActor"). 

    Code:
    ....
    //sample code for used class
    UClass()
    class Test : public AActor {
      .....
      public:
         void test();  
      ....
    }
    At first I call: 

    Code:
    //FLatentActionInfo isn't document well what it does and when, or I can't find enough information about it
    UGameplayStatics::LoadStreamLevel(this, "map1", true, true, FLatentActionInfo())
    Later ingame "ENTER" is pressed and I want to stream another level, as I had done it with blueprints before for testing.

    Code:
    UGameplayStatics::LoadStreamLevel(this, "map2", true, true, FLatentActionInfo()) 
    UGameplayStatics::UnloadStreamLevel(this, "map1", FLatentActionInfo())
    The first call loads the map correctly. The second call for "map2" loads also correctly but then the "map1" isn't unloaded. The documentation says that the next call isn't processed until the first call is finished ("Stream the level with the LevelName ; Calling again before it finishes has no effect.").

    The should be the point why "map1" isn't unloaded because "map2" is currently loaded and not finished at this point.

    I also tried to fill the FLatentActionInfo struct with

    Code:
    FLatentActionInfo info;
    info.CallbackTarget=this;
    info.ExecutionFunction="test";
    info.UUID=12345;
    and called 

    Code:
    UGameplayStatics::LoadStreamLevel(this, "map1", true, true, info)
    I expected that the callback is called if the loading operation was done but the method "test" is never called.

    So I wondering about how I can achive it.

    If anyone could explain this for me it would be really really great or have a short information which points in the correct direction.

    Thank you in advance and have a nice day so far.

    Regards

    -freakxnet
    Last edited by freakxnet; 08-05-2014 at 06:34 PM.
    Quick reply to this messageReply   Reply With QuoteReply With Quote   Multi-Quote This Message     
  2. #2
    0
    Unreal Engine Developer
    Join Date
    Mar 2014
    Posts
    101
    Hi,

    It's much easier to manage level streaming in blueprints instead of C++.
    Take a look at GetStreamingLevel BP node. It gives you full control over level streaming.

    Name:  levelstreaming_1.png
Views: 1840
Size:  55.4 KB

    Name:  levelstreaming_2.png
Views: 1843
Size:  59.8 KB
    Quick reply to this messageReply   Reply With QuoteReply With Quote   Multi-Quote This Message     
  3. #3
    0
    Supporter
    Join Date
    Aug 2014
    Posts
    4

     !!!solved!!!

    Thank you for your post. With blueprints the streaming isn't a problem. So but I want to have it in Code ;-).

    So for all who wants to integrate level streaming within C++ code here's the solution:

    I thought about the callback function of the FLatentActionInfo structure.
    You have to define:

    Code:
    FLatenActionInfo info;
    info.CallbackTarget = *myObjectWithDerivesFromUObject;
    info.ExecutionFunction = "myFunctionToCall";
    info.UUID = 1;
    info.Linkage = 0;
    Normally you would give a function pointer to got access to a callback method. But here you give a method name String. Now for Java, when I does reflection related stuff I use often strings for method / member access. Also for this problem. A string to use is only possible if the method name is resolved by the reflection system.

    Then the solution is easy:

    You have to define the method within the UE4 reflection system. After I had added the UFUNCTION macro the method was instantly called. 

    Code:
    UCLASS()
    class TestClass : public AActor {
        public:
           UFUNCTION(BlueprintCallable, Category = Game)
           void myFunctionToCall();
    
    };
    Now this is possible: 

    load "map1" => callback1 => unload "map1" => callback => load "map2" and voila it's done. The content of "map1" is disappeared and only "map2" stays loaded.

    Wrapped into a new controller class its now a simple task to stream levels. But don't forget to add them within UE4 => MainMenu:Window => Levels.

    Code:
    FLatenActionInfo info;
    info.CallbackTarget = *myObjectWithDerivesFromUObject;
    info.ExecutionFunction = "m


반응형
반응형

Pure vs. Impure

함수는 Pure (순수하)거나 Impure (비순수) 중 하나입니다. 주요 차이점이라면 순수 함수는 어떤 식으로든 클래스의 멤버나 상태를 변경하지 않기로 약속한 반면, 비순수 함수는 자유롭게 상태를 변경할 수 있습니다. 순수 함수는 일반적으로 값을 구해오거나 데이터 값을 출력하기만 하는 작업에 사용됩니다.

비순수 함수는 EventGraph 에서 실행 핀을 Function Call 노드 에 연결하여 명시적으로 실행해야 합니다. 비순수 함수는 다음 방법 중 하나를 사용하도록 디자인되었습니다:

  • 코드에 정의된 UFUNCTION 에 대한 UFUNCTION 선언에서 BlueprintCallable 키워드를 지정합니다.

  • 블루프린트 에디터 를 통해 추가된 함수의 경우 Pure 박스의 체크를 해제시켜 둡니다.

순수 함수는 데이터 핀으로 연결되며, 그에 관련된 데이터가 필요할 때 컴파일러가 자동으로 실행해 줍니다. 즉 순수 함수는 연결된 노드마다 한 번씩 호출된다 는 뜻입니다. 순수 함수는 다음 방법 중 하나를 사용하도록 디자인되었습니다:

  • 코드에 정의된 함수들에 대한 함수 선언에서 BlueprintPure 키워드를 지정합니다.

  • 블루프린트 에디터 를 통해 추가된 함수의 경우 Pure 박스를 체크합니다.


반응형
반응형

함수 오버라이드 시에는 반환 노드를 추가 하고 반환 변수를 하나 추가해 줘야

블루프린트에서 함수 오버라이드를 할 수 있다..(머야 ㅡ.ㅡ;)

Overriding a function creates an Event instead of making a new function

1

In 4.8.1, I have a class where if I override a function in a child class, an event will be created by the name of the function instead of creating a new function. Other classes and their children will properly do this.

Is there a setting that changes this functionality, or is there something funky going on here?

Product Version: UE 4.8
Tags:
more ▼

asked Jun 30 '15 at 4:21 AM

JoystickMonkey gravatar image

JoystickMonkey 
68  1  4  10


1 answer:sort voted first 
1

Yeah have the same bug. It seems like event is created instead of function if overridable function has not return value. So what I'm doing - is:

1) Create a function in parent class. Ex SomeFunction.

2) Make this function to return a some Boolean value (in Outputs section.)

3) Override this function in child class (it's now should create as normal function, not like event.)

4) Delete Boolean value in parent.

5) Delete Boolean value in child.

6) Compile parent class.

7) Compile child class.

P.S. I'm using 4.11 of UE.



https://answers.unrealengine.com/questions/250023/overriding-a-function-creates-an-event-instead-of.html#answer-417889

반응형
반응형

컨스트럭션 스크립트는 액터가 씬에 배치 될 때 실행 되는 블루프린트이다






컨스트럭션 스크립트

https://docs.unrealengine.com/latest/KOR/Engine/Blueprints/UserGuide/UserConstructionScript/index.html

  • SHARE:

언리얼 엔진

Construction Script (컨스트럭션 스크립트)는 블루프린트 클래스의 인스턴스 생성시 컴포넌트 리스트 다음에 실행되는 부분입니다. 여기에는 노드 그래프가 들어있어 블루프린트 클래스 인스턴스에서 초기화 작업을 할 수 있습니다. 이는 월드로의 트레이스, 메시와 머티리얼 설정 등의 작업을 맥락에 따라 이루어지도록 구성할 수 있는 매우 강력한 기능입니다. 예를 들어 라이트 블루프린트는 어떤 종류의 바닥에 놓이는가에 따라 지정된 메시 중에서 올바른 메시를 선택하도록 할 수도 있고, 펜스 블루프린트의 경우 각 방향으로 트레이스 작업을 하여 펜스 길이를 얼마나 길게 할 것인지를 결정할 수도 있습니다.

블루프린트 클래스에만 컨스트럭션 스크립트 가 존재합니다. 레벨 블루프린트에는 없습니다.

컨스트럭션 스크립트 그래프의 실행 입구는 항상 존재하는 ConstructionScript 노드입니다.

construction_script.png

그래프 패널 작업

Graph, 그래프는 특정 노드 그래프의 시각적 표현을 나타내며, 그래프에 포함된 모든 노드는 물론 그 사이의 연결 관계를 표시합니다. 노드의 추가 제거, 노드 배치, 노드간의 링크 생성 등을 위한 편집 기능이 제공됩니다. 그래프 에서 Breakpoint (중단점)을 설정하여 블루프린트디버깅 을 수월하게 할 수도 있습니다.

블루프린트 안에서 컨스트럭션 스크립트 와 기타 그래프 작업 관련 상세 안내는 그래프 에디터 탭 문서를 참고해 주시기 바랍니다.

반응형
반응형



마티네 트랙

Event 트랙



https://docs.unrealengine.com/latest/KOR/Engine/Matinee/TrackReference/index.html

Event(이벤트) 트랙은 시퀀스의 특정 시점에 블루프린트에 도로 알리는 이벤트를 발동하는 메커니즘을 마티네에 주는 트랙입니다. 이벤트 트랙에 키프레임을 놓을 때, 이벤트 이름 을 물어옵니다. 각 고유 이벤트 이름 은 마티네 액션에 새로운 출력 핀을 만들게 됩니다. 시퀀스가 이벤트 키에 달하면 해당 출력에 연결된 블루프린트 노드가 활성화되게 됩니다. 동일한 이름의 키가 여럿 있을 경우 출력 핀은 하나만 생성되나, 키 각각이 전달될 때마다 활성화되게 됩니다.

여기 'ToggleLight' 라는 키가 하나 있는 이벤트 트랙입니다.

event_track.png

그리고 이것은 블루프린트의 마티네 액터로, 새로운 출력 단자가 보이며, 여기에 연결하여 이벤트를 발동시킬 수 있습니다.

event_connector.png

이벤트 트랙 헤더의 eventarrows.jpg 버튼을 통해 시퀀스가 정방향 재생, 역방향 재생, 혹은 둘다의 경우에 출력을 발동시킬지 여부를 조절할 수 있습니다. 오른 화살표 버튼이 노랑이면, 해당 트랙의 이벤트는 시퀀스가 정방향으로 재생될 때 전달되면서 발동되게 됩니다. 왼쪽 화살표 버튼이 노랑이면, 시퀀스가 역방향 재생될 때 이벤트가 발동되게 됩니다.

이벤트 트랙 이 어느 그룹에 있든지, 액터 가 그룹에 붙어있든 말든 상관 없이, 마티네 액터 는 트랙 에 놓인 각 키마다 출력 단자를 생성합니다. 이벤트 키에 우클릭하면 이름을 바꿀 수 있습니다. 그리 하면 이름이 같은 다른 키는 물론 마티네 액터의 출력 단자 이름도 바뀌게 됩니다.

디테일 패널에서 이 트랙 에 대해 조절할 수 있는 프로퍼티 는 아래와 같습니다.

프로퍼티설명
Active Condition활성화 조건 - 언제 트랙이 켜질지를 정합니다. 항상, 고어가 켜졌을 때, 고어가 꺼졌을 때 등입니다.
Fire Events When Backwards역방향일 때 이벤트 발동 - True 면 이 트랙용 이벤트는 마티네가 역방향으로 재생할 때 발동됩니다.
Fire Events When Forwards정방향일 때 이벤트 발동 - True 면 이 트랙용 이벤트는 마티네가 정방향으로 재생할 때 발동됩니다.
Fire Events When Jumping Forward정방향으로 점프할 때 이벤트 발동 - True 면 마티네를 건너뛰어도 트랙의 모든 이벤트가 발동될 수 있게 합니다.



반응형
반응형

액터 소멸

https://docs.unrealengine.com/latest/KOR/Programming/UnrealArchitecture/Actors/index.html

액터는 일반적으로 가비지 콜렉팅되지 않는데, 월드 오브젝트가 액터 레퍼런스 목록을 저장하기 때문입니다. 액터는 Destroy() 를 호출하여 명시적으로 소멸시킬 수 있습니다. 그러면 레벨에서 제거되어 pending kill (킬 대기) 상태로 마킹, 잠시 후 다음 가비지 콜렉션 때 지워진다는 뜻입니다.

반응형
반응형

커서아래 클릭한(Hit)한 오브젝트를 가져오는 함수 

Get Hit Result Under Cursor for Objects


https://docs.unrealengine.com/latest/INT/BlueprintAPI/Game/Player/GetHitResultUnderCursorforObject-/index.html


  • SHARE:

Get Hit Result Under Cursor for Objects

Target is Player Controller

Get Hit Result Under Cursor for Objects
Target
Object Types
Trace Complex
Hit Result
Return Value

Inputs

Target
Player Controller Reference
Object Types
Array of EObjectTypeQuery Enums
Trace Complex
Boolean

Outputs


Hit Result
Hit Result Structure
Return Value
Boolean


반응형
반응형

DoN


http://docs.unrealengine.com/latest/KOR/Engine/Blueprints/UserGuide/FlowControl/index.html?utm_source=editor&utm_medium=docs&utm_campaign=rightclick_bpnode#doonce

DoN Example

DoN (N 번 실행) 노드는 실행 신호를 N 번 발동시킵니다. 한계치에 도달한 이후에는 Reset 입력에 신호가 전송될 때까지 나가는 실행 신호를 중지합니다.

예를 들어 탈것의 시동을 스무 번 건 다음에는, Reset 입력이 활성화되었을 때에 묶여있는 연료보급 이벤트시까지 시동이 걸리지 않는 것입니다.

클릭하면 크게 볼 수 있습니다.

항목설명

입력 핀

EnterDoN 검사를 트리거시키는 실행 입력입니다.
nDoN 노드 트리거 횟수를 설정하는 입력입니다.
ResetDoN 노드가 다시 트리거될 수 있도록 리셋시키는 실행 입력입니다.

출력 핀

ExitDoN 이 N 번 이상 트리거되지 않았을 때, 또는 Reset 입력이 호출되었을 때만 트리거되는 실행 핀입니다.

DoOnce

DoOnce_Example.png

DoOnce (한 번 실행) 노드는 이름 그대로 실행 신호를 한 번만 발동시킵니다. 그 시점부터는 Reset 입력에 신호를 별도로 주지 않는 이상 실행 신호를 내보내지 않습니다. 이 노드는 DoN 노드에서 N = 1 일때와 같습니다.

예를 들어 DoOnce 를 통해 문을 여는 네트워크를 만들었다면 그 문은 한 번만 열리게 됩니다. 그러나 Reset 에 트리거를 묶어 두고서 그 트리거가 활성화되면 문이 다시 열리도록 할 수도 있습니다.

클릭하면 더 크게 볼 수 있습니다.

항목설명

입력 핀

(무제)DoOnce 검사를 발동시키는 실행 입력입니다.
ResetDoOnce 노드가 다시 발동될 수 있도록 리셋시키는 실행 입력입니다.

출력 핀

Completed아직 DoOnce 가 발동되지 않았거나 Reset 입력이 호출된 경우에만 발동되는 실행 핀입니다.


반응형
반응형

  • SHARE:
언리얼 엔진

pawn_ball.png

Pawn 클래스는 플레이어나 AI 가 제어할 수 있는 모든 액터의 베이스 클래스입니다. Pawn 은 월드 내 플레이어나 AI 개체에 대한 물리적 표현입니다. 이는 플레이어나 AI 개체의 시각적인 모습 뿐만 아니라, 콜리전이나 기타 물리적 반응과 같은 측면에서 월드와의 상호작용 방식도 Pawn 이 규정한다는 뜻입니다. 특정 유형 게임에서는 게임 내에 눈에 보이는 플레이어 메시나 아바타가 없기에 헛갈릴 수가 있습니다. 그와는 무관하게 Pawn 은 여전히 게임 내 플레이어나 개체의 물리적 위치, 방향 등을 나타냅니다. Character (캐릭터)는 걸어다닐 수 있는 능력을 지닌 특수 유형 Pawn 을 말합니다.

기본적으로 Controller 와 Pawn 에는 1:1 대응 관계가 있습니다. 즉 각 콘트롤러는 어느 때고 단 하나의 폰만을 제어합니다. 마찬가지로 게임플레이 도중 스폰된 폰이 자동적으로 콘트롤러에 빙의(possess)되지는 않습니다.

블루프린트에서, 폰 파생 클래스에 동작을 추가하는 가장 좋은 방법은 SetActorLocation 입니다. 이를 통해 해당 위치로 순간이동시킬지, 아니면 sweep 시킬지를 결정할 수 있습니다. sweep 이란 폰을 해당 방향으로 이동시키다가 무언가에 걸리면 멈추게 하는 것을 말합니다.




디폴트 폰


http://docs.unrealengine.com/latest/KOR/Gameplay/Framework/Pawn/index.html?utm_source=editor&utm_medium=docs&utm_campaign=rich_tooltips

Pawn 클래스가 월드의 플레이어나 AI 개체의 물리적 표현을 만드는 데 있어 꼭 필요한 것만 제공해 주는 반면, DefaultPawn 서브클래스에는 추가적인 컴포넌트와 함수성이 딸려 옵니다.

DefaultPawn 클래스에는 네이티브 DefaultPawnMovementComponent, 구체형 CollisionComponent, StaticMeshComponent 가 들어 있습니다. DefaultPawnMovementComponent 와 카메라 제어는 물론 기본 이동 바인딩 추가를 위한 불리언 역시 DefaultPawn 클래스에 존재하며, 기본값은 True 로 설정되어 있습니다.

DefaultPawnMovementComponent

DefaultPawnMovementComponent 에 대한 기본 이동 스타일은 무중력 비행으로 설정되어 있습니다. 보통의 MovementComponent 변수 외에 MaxSpeedAccelerationDeceleration 플로트 값이 포함되어 있습니다. 이 세 가지 변수는 DefaultPawn 파생 블루프린트에서도 접근 가능합니다.




관람자 폰

SpectatorPawn 클래스는 DefaultPawn 의 서브클래스입니다. GameMode 를 통해 Pawn 과 SpectatorPawn 에 대해 다양한 클래스를 기본으로 지정할 수 있으며, 이 클래스는 관람에 이상적인 단순한 프레임워크를 제공합니다. DefaultPawn 과 마찬가지로 구체형 CollisionComponent 가 있긴 하나 .DoNotCreateDefaultSubobject(Super::MeshComponentName) 구현때문에 StaticMeshComponent 는 생성되지 않습니다. SpectatorPawn 클래스에 대한 이동은 SpectatorPawnMovementComponent 에서 처리되며, 무중력 비행 동작은 DefaultPawnMovementComponent 에서와 마찬가지이고, 여기에 필요에 따라 시간 지연을 처리하거나 무시할 수 있는 코드가 추가되어 있습니다.


반응형
반응형


액터 레퍼런싱

https://docs.unrealengine.com/latest/KOR/Engine/Blueprints/UserGuide/Types/LevelBlueprint/index.html#액터레퍼런싱

종종 레벨 블루프린트 에서 노드의 Target 핀에 액터에 대한 레퍼런스를 연결해 줄 일이 있습니다. 액터 레퍼런스를 지닌 노드를 얻으려면:

  1. 레벨 뷰포트 나 월드 아웃라이너 에서 액터를 선택합니다.

    selected_actor.png

  2. 레벨 블루프린트 를 엽니다.

    Level Blueprint Button

  3. 그래프에서 노드를 추가하려는 곳에 우클릭합니다.

  4. 나타나는 맥락 메뉴에서 Add Reference to [SelectedActor] ([선택된 액터]에 대한 레퍼런스 추가)를 선택합니다.

    add_reference_to.png

또는:

  1. 월드 아웃라이너 탭에서 액터 를 끌어 레벨 블루프린트 의 그래프 안에 놓습니다.

    add_reference_drag_drop.png

나타나는 액터 레퍼런스 노드는 호환되는 타겟 핀에 연결할 수 있습니다.

actor_reference.png

어떤 경우에는 레퍼런스 노드가 필요치 않은데, 올바른 유형의 출력 핀을 타겟 입력 핀에 연결할 수 있기 때문입니다.

target_pin_noref.png



반응형
반응형

마티네는 언리얼 내부에서 지원하는 툴로 엑터나 오브젝트에 대한 애니메이션/시퀀스를 만들 수 있다

간단히 말해 특정 애니를 마티네로 작업 할 수 있고 게임 내에서 특정 조건에 해당 애니를 출력 하는 방식이다

좀 더 나아가 마티네의 활용은 굉장히 다양하다 값으로 여길 수 있는 것은 모두 애니메이션 시퀀스로 만들어

원하는 시퀀스를 원하는 시점에 플레이 할 수 있는데 이 것은 위치는 물론 색상값이나 라이팅과 좀 더 인터렉티브한 트리거의 활용 등도 가능하다




Level Blueprint (레벨 블루프린트)란 레벨 단위 글로벌 이벤트 그래프 역할을 하는 특수한 형태의 블루프린트 입니다. 프로젝트 내 각 레벨에는 기본적으로 자체적인 레벨 블루프린트 가 있어 언리얼 에디터 안에서 편집할 수 있으나, 에디터 인터페이스를 통해 새로운 레벨 블루프린트 를 생성할 수는 없습니다.

레벨 전체적으로 관련된 이벤트 또는 레벨 내 특정 액터 인스턴스가 함수 호출이나 흐름 제어 연산 형태로 일련의 동작을 발동시키는 데 사용됩니다. 언리얼 엔진 3 에 익숙하신 분들이라면 그 키즈멧 작동 방식과 매우 유사한 이런 개념에 금방 익숙해 지실 수 있을 것입니다.

레벨 블루프린트 는 레벨 스트리밍 과 마티네 를 제어하는 방편이 되기도 하며, 레벨에 놓인 액터에 이벤트를 바인딩하는 데 쓰이기도 합니다.

(레벨  블루 프린트에서 마티네 제어가 가능한듯.... 아놔.. 이거 찾느라 고생좀 함)

레벨 블루프린트 UI 관련 상세 정보는, 레벨 블루프린트 UI 문서를 참고하세요.



https://docs.unrealengine.com/latest/KOR/Engine/Matinee/HowTo/MHT_1/index.html


마티네 사용


문 구성하기

  • SHARE:

언리얼 엔진


다음 단계에서는 트리거 볼륨에 들어가고/나갈 때 열리고/닫히는 간단한 문을 만들어 보겠습니다.

프로젝트 생성하기

이 섹션에서는 프로젝트를 셋업해 봅니다.

  1. 언리얼 프로젝트 브라우저 창에서 새 프로젝트 를 생성한 다름 블루프린트 삼인칭 템플릿을 사용합니다.

    MatineeHowTo.jpg

  2. 시작용 콘텐츠 포함 옵션이 켜졌는지 확인합니다.

  3. 프로젝트에 이름을 붙입니다.

  4. 위 각각을 정의한 상태로, 프로젝트 생성 을 클릭하여 새 프로젝트를 만듭니다.

문과 트리거 배치하기

이번 단계에서는 문을 배치하고 그 문에 트리거를 추가합니다.

  1. 콘텐츠 브라우저 안에서 Props 폴더를 찾아 선택한 다음 SM_DoorFrame 스태틱 메시를 찾습니다.

    MHT1_DoorFrame.png

    Props 폴더가 보이지 않는 경우, 프로젝트 생성하기 단계를 참고하여 시작용 콘텐츠 포함 을 체크했는지 확인하시기 바랍니다._

  2. SM_DoorFrame 스태틱 메시에 클릭한 다음 레벨 뷰포트 에 끌어 놓습니다.

    MHT_DoorFrameDragIn.jpg

  3. 또 Props 폴더에서 SM_Door 스태틱 메시를 찾은 다음 레벨 뷰포트 에 끌어 놓습니다.

    MHT_DoorDragIn.jpg

  4. 콘텐츠 브라우저 에서 SM_Door 스태틱 메시를 다시 찾은 다음 더블클릭하여 스태틱 메시 뷰어에서 엽니다.

  5. 디테일 패널의 검색창에서 Collision 이라 입력한 다음 Collision Complexity 를 Use Complex Collision as Simple 로 설정합니다.

    MHT_CollisionComplexity.jpg

    위 단계로 문에 콜리전이 적용되도록 합니다._

  6. 레벨 뷰포트 에서 SM_Door 를 선택한 상태로 디테일 패널을 찾습니다. 트랜스폼 아래 회전 세팅에서 Z 값을 -180 으로 설정합니다.

    MHT1_RotateDoor.png

    -179.99 로 자동 조정되는데 괜찮습니다._

  7. 이동 위젯을 사용하여 문을 문틀 안에 위치시킵니다.

    MHT1_MoveDoor.png MHT1_MoveDoor2.png

  8. 모드 메뉴의 기본 탭 아래 박스 트리거 를 찾아 레벨 뷰포트 의 문틀 안에 끌어 놓습니다.

    MHT_DragInBoxTrigger.jpg

  9. 디테일 패널에서 TriggerBox 를 선택한 다음 Shape 섹션에서 Box Extent 에 대한 X 값을 140 으로 변경합니다.

    MHT1_TriggerBoxSize.png

    주: 문이 안쪽으로 열리므로, Trigger Box 는 문틀 넘어 안쪽까지 늘어뜨려 (플레이어가 접근하기 전) 조금 더 일찍 열리도록 합니다.

    블루프린트 를 사용하여 TriggerBox 에 플레이어가 들어서는 방향에 따라 각기 다른 방향으로 열리는 문 예제를 2.4 - 트리거 달린 문 콘텐츠 예제에서 찾아보실 수 있습니다.

  10. 문과 트리거가 배치되었으니, 마티네 액터를 추가하여 열고/닫아 주겠습니다.

마티네 액터 추가하기

이번 단계에서는 마티네 액터를 추가한 다음 키프레임 을 설정하여 문을 열고/닫아 주겠습니다.

  1. 툴바 메뉴에서 마티네 를 선택한 다음 마티네 추가 버튼을 클릭합니다.

    MHT_AddMatinee.jpg

  2. 마티네 되돌리기 경고창이 뜹니다. 계속 버튼을 클릭하세요.

    MHT1_MatineeWarning.png

  3. 마티네 에디터 창이 열립니다.

    클릭하면 원래 크기로 볼 수 있습니다.

  4. 트랙 창 (All 아래 빈 곳)에 우클릭한 다음 맥락 메뉴에서 새 빈 그룹 추가 를 선택합니다.

    MHT1_TrackContextMenu.png

  5. 그룹에 새 그룹 이름 을 지으라는 창이 뜨면 이 그룹의 이름을 지어줍니다 (이 예제에서는 Door 라 하겠습니다).

  6. 마티네 창을 최소화시킨 다음 메인 에디터 에서 월드 아웃라이너 창을 찾아 SM_Door 를 선택하여 강조시킵니다.

    MHT1_SelectDoor.png

  7. 마티네 창으로 돌아와 그룹(Door)에 우클릭하여 맥락 메뉴를 띄운 다음, 액터 를 선택하고 선택된 액터를 추가 를 선택합니다.

    MHT1_AddDoorToGroup.png

    그러면 Door 그룹에 SM_Door 액터가 추가됩니다._

  8. 그룹 (Door) 에 다시 우클릭하여 맥락 메뉴를 띄운 다음 새 Movement Track 추가 를 선택합니다.

    MHT1_AddMovementTrack.png

  9. Movement Track 이 추가되면 새로운 키프레임 이 트랙상의 0.00 시간에 자동으로 추가됩니다 (아래 1 참고)

    MHT1_TrackExplained.png

    주: 섹션 2 에는 시작/끝 마커 (빨강 삼각형), 루프 섹션 (초록 삼각형), 시간 바 (검정 바)가 있습니다.

  10. 시간 바 에 클릭한 다음 시간을 0.50 으로 끌어놓고서 Enter 키를 쳐 새 키프레임 을 추가합니다.

    MHT1_AddKey.png

  11. 마티네 창을 최소화시킨 다음 레벨 뷰포트 로 돌아갑니다. SM_Door 가 선택된 상태에서, E 키를 쳐 회전 모드로 들어갑니다.

    MHT1_RotateWidget.png

  12. 회전 위젯의 파랑 원호를 클릭한 다음 (위젯이 바뀝니다) 오른쪽으로 -90.0 도 회전시킵니다.

    MHT1_DoorOpen.png

  13. 마티네 창으로 돌아가 빨강 화살표 끝 마커 를 클릭한 다음 왼쪽 0.50 으로 옮깁니다.

    MHT1_EndPointMoved.png

  14. 마티네 시퀀스 셋업이 완료되었습니다. 다음 단계에서는 마티네 를 트리거 에 걸어 마무리하겠습니다.

마티네 를 트리거 박스 에 걸어주기

이번 단계에서는 마티네 를 트리거 박스 에 걸어 트리거에 들어갈 때 열리고 나갈 때 닫히도록 만들겠습니다.

  1. 툴바 메뉴에서 블루프린트 를 선택한 다음 레벨 블루프린트 열기 버튼을 클릭합니다.

    MHT_OpenLvlBlueprint.jpg

  2. 레벨 블루프린트 를 최소화시킨 다음 레벨 뷰포트 또는 월드 아웃라이너 를 통해 MatineeActor 를 클릭하여 선택합니다.

    MHT1_MatineeSceneOutliner.png

  3. 레벨 블루프린트 창을 열고 이벤트 그래프 에 우클릭한 다음 맥락 메뉴에서 MatineeActor 로의 레퍼런스 추가 옵션을 선택합니다.

    MHT_MatineeReference.jpg

  4. 그러면 MatineeActor 가 레벨 블루프린트 의 이벤트 그래프 에 추가됩니다.

    MHT1_MatineeAddedToBP.png

  5. 레벨 블루프린트 를 최소화시킨 다음 레벨 뷰포트 또는 월드 아웃라이너 를 통해 TriggerBox 에 클릭하여 선택합니다.

    MHT1_TriggerBoxSceneOutliner.png

  6. 레벨 블루프린트 창을 열어 이벤트 그래프 에 우클릭한 다음 맥락 메뉴에서 Add Event for TriggerBox > Collision > Add OnActorBeginOverlap 을 선택합니다.

    MHT1_AddOnBeginOverlap.png

  7. 다시 이벤트 그래프 에 우클릭한 다음 기존 단계를 반복하여 Add OnActorEndOverlap 옵션을 추가합니다.

    MHT1_AddOnEndOverlap.png

  8. 이벤트 그래프 에서 MatineeActor 노드를 찾아 클릭한 다음 출력 핀(파랑 원)을 끌어 놓아 맥락 메뉴를 띄우고, 검색창에 Play 라 입력한 다음 Play 옵션을 선택합니다.

    MHT1_DragOffPlay.png

  9. MatineeActor 노드에서 다시 한번 끌어놓아 맥락 메뉴 검색창에서 Reverse 를 입력한 다음 Reverse 옵션을 선택합니다.

    MHT1_DragOffReverse.png

  10. OnActorBeginOverlap 노드를 찾아 실행 출력 핀을 끌어 Play 노드의 입력 핀에 연결합니다.

    MHT1_ConnectOverlapToPlay.png

  11. 위 단계를 반복하여 OnActorEndOverlap 노드의 출력을 Reverse 노드의 입력 핀에 연결합니다.

    MHT1_BlueprintConnected.png

  12. 레벨 블루프린트 의 툴바 메뉴에서 컴파일 버튼을 클릭합니다.

    MHT1_ClickCompile.png

  13. 블루프린트 컴파일이 완료되어 TriggerBox 가 이제 마티네 액터에 걸렸습니다.

  14. 레벨 블루프린트 를 최소화시킨 다음 메인 툴바의 플레이 버튼을 눌러 에디터에서 플레이합니다.


반응형
반응형


ETC1 VS ETC2

http://hwanggoon.tistory.com/237 


 

ETC 포맷에 대해 알아보자

 

 

ETC는 Ericsson Texture Compression의 약자로 에릭슨에서 만든 텍스쳐 포맷 입니다.

참조 : http://www.jacobstrom.com/publications/StromAkenineGH05.pdf

안드로이드 표준 포맷이기도 합니다.

 

ETC1은 Open GL ES2.0에서 사용 할 수 있는 포멧입니다.

요즘 모바일 게임 개발에 널리 사용되고 있죠.

ETC1의 단점 중 하나는 사용 Bit수가 작다 보니 압축 시 채널 별 색상 침범이 눈에 띄게 일어 난다는 겁니다.

그래서 R채널은 반투명, G채널은 마스크 이런 식으로 사용하면 문제가 될 수 있습니다.

 

자 그렇다면 ETC2는?

ETC1에 비해 퀄리티도 좋고, 색상침범도 훨씬 덜 일어 납니다.

아래 내용을 보시죠.

 

 

 

ETC1, ETC2 비교

 

 

퀄리티 비교

 

참조 : https://www.khronos.org/assets/uploads/developers/library/2012-siggraph-opengl-es-bof/Ericsson-ETC2-SIGGRAPH_Aug12.pdf

ETC1과 ETC2의 퀄리티 차이를 분명히 볼 수 있죠.

ETC2의 퀄리티는 DXTC 포맷 수준의 퀄리티를 보장합니다.

 

512*512 사이즈, 반투명 채널 X

 - ETC1 : 128KB

 - ETC2 : 128KB

 

512*512 사이즈, 반투명 채널 O (알파테스팅)

 - ETC1 : 256KB (ETC1 2장 사용)

 - ETC2 : 128KB

알파테스팅 용 반투명 채널을 사용한다면 ETC2가 용량을 2배 절약

(마젠타 방식을 사용하면 용량은 같습니다.)

 

512*512 사이즈, 반투명 채널 O (알파블랜딩)

 - ETC1 : 256KB (ETC1 2장 사용)

 - ETC2 : 256KB

퀄리티는 ETC2가 훨씬 좋습니다.

 

 

알파채널 비교

순서대로 ETC2 8bit, RGBA 16bit, RGBA 32bit

ETC2의 용량은 256KB로 다른 포멧에 비해 용량 대비 퀄리티가 압도적 입니다.

(UI를 ETC2로 제작 한다면 상당한 효과를 볼 수 있을 겁니다.)

 

ETC2의 압승입니다.

 

 

 

포맷 지원

 

 

ETC는 안드로이드 표준 포맷이라 대부분의 기기에서 지원 합니다.

다만 버전 별로 지원하는 기준이 있는데요.

 

ETC1 : Open GL ES2.0

ETC2 : Open GL ES3.0, Open GL ES4.3

 - 3.0부터 의무 지원

 - 참조 : https://en.wikipedia.org/wiki/Ericsson_Texture_Compression#ETC2_and_EAC

 

 

Open GL ES3.0 안드로이드 디바이스

 - 참조 : https://en.wikipedia.org/wiki/OpenGL_ES#OpenGL_ES_3.0

 - Nexus 7 (2013)
 - Nexus 4
 - Nexus 5
 - Nexus 10
 - HTC Butterfly S
 - HTC One/One Max
 - LG G2
 - LG G Pad 8.3
 - Samsung Galaxy S4 (Snapdragon version)
 - Samsung Galaxy S5
 - Samsung Galaxy Note 3
 - Samsung Galaxy Note 10.1 (2014 Edition)
 - Sony Xperia M
 - Sony Xperia Z/ZL
 - Sony Xperia Z1
 - Sony Xperia Z Ultra
 - Sony Xperia Tablet Z

...

..

.

 

 

Open GL ES2.0에서 ETC2

 

 

2.0버전에 ETC2를 사용하면 텍스쳐는 보일까?

 - 잘~ 보입니다.(유니티에서는...)

 

유니티에서는 텍스쳐 포맷이 맞지 않는데도 어떻게 텍스쳐가 보일까?

 - 유니티는 지원하는 않는 포맷을 사용한 경우, 내부적으로 적용 가능한 텍스쳐를 생성해 보여 줍니다.

 

그럼 ETC2를 사용해도 되지 않나?

 - 내부적으로 생성된 텍스쳐가 RGBA32여서 문제

 - 메모리에 올라가는 텍스쳐 용량이 증가하게 됨

 - 증가된 용량을 받아 주는 모바일 기기라면 문제 없겠지만, 그게 아니라면 앱이 죽게 되겠죠.

 

그럼 ETC2를 사용하면 안되나요?

 - 전체 메모리가 낮은 편이라면 ETC2를 써도 괜찮습니다.

 - 메모리의 압박을 받는 상황이라면 사용하면 안되겠죠.

 

 


Open GL 버전 별 점유율

 

 

참조 : http://developer.android.com/about/dashboards/index.html

2015년 10월 2일 기준 OpenGL 점유율 입니다.

아직까진 2.0을 많이 사용하고 있네요.

그런데 3.0 비율이 43%(3.0 + 3.1)로 생각보다 높습니다.

 

2015년 2월 2일 기준이 31.1%인걸 감안하면 빠르게 교체되고 있는 중 입니다.

(8개월 만에 12%가 올라갔네요.)

 

이 추세대로 간다면 내년 여름 즘 3.0이 60%정도 되지 않을까 싶습니다.

 

 

 

종합 분석

 

 

글로벌 서비스를 생각한 모바일 게임이라면 아직까진 ETC1으로 가야할 것 같습니다.

(노트3, 겔럭시4 LTE-A 버전 이상을 생각한다면 ETC2로 가야겠지만..)

 

고 퀄리티 게임을 목표로 상위 기종을 노린다면 ETC2가 좋은 방법이 될 수 있습니다.

2017년을 목표로 개발을 하는 프로젝트는 ETC2로~

(Open GL ES3.0이면 쉐이더 텍스코드도 더 쓸 수 있고, 개발 방법에 많은 변화가 생길 것 같네요.)





1. Android Works 설치


http://docs.unrealengine.com/latest/KOR/Platforms/Android/GettingStarted/1/index.html



안드로이드 개발을 시작하기에 앞서 먼저 Android Works 를 설치해야 합니다. Android Works 는 안드로이드 디바이스에 디플로이하기 위해 필요한 프로그램과 코드 전부 설치되도록 도와줄 것입니다. 여기서는 개발 PC 에 Android Works 를 설치하는 법에 대해 다루겠습니다.

운영 체제 선택

Windows

Mac OS

이미 Android Works 가 설치되어 있는데 환경 변수는 없어진 경우, 이 단계는 전부 건너뛰고 에디터의 편집 메뉴 -> 프로젝트 세팅 -> Android SDK 프로퍼티에서 설치 위치를 지정해 주기만 해도 됩니다.

Android Works 는 에디터와 런처 둘 다 닫힌 상태로 설치할 것을 강력 추천합니다. 그래야 설치에 문제가 없습니다.

  1. Android Works 를 설치하려면 Engine > Extras > Android 폴더로 이동합니다.

    설치 유형위치
    바이너리[EngineInstallLocation]\Unreal Engine[EngineVersion]\Engine\Extras\Android
    GitHub[EngineSyncLocation\UE4\Engine\Extras\Android

    UE4 를 Github 에서 다운로드한 경우, Android Works 인스톨러 실행 전 다음과 같은 작업을 해 줘야 합니다. GitHub 에서 UE4 소스 코드를 다운로드했으면 윈도우 기반 PC 든 맥이든 양쪽에 적용된다는 점 참고 바랍니다. 런처에서 다운로드한 바이너리 빌드를 사용중이라면 이 부분은 건너뛰고 바로 Android Works 설치로 들어가시면 됩니다.

    1. GitHub 에서 UE4 다운로드를 마치고 압축을 풀었으면, Setup.bat 파일을 실행하여 필수 파일과 Android Works인스톨러를 다운로드합니다.

    2. Setup.bat 실행이 완료되면 Android Works 인스톨러를 실행하고 아래 안내를 따릅니다.

  2. AndroidWorks-1R1-windows.exe 파일을 더블클릭하여 설치 프로세스를 시작합니다.

    AndroidWorks_11.png

  3. 첫 창에서 다음 버튼을 눌러 설치 프로세스를 시작합니다.

    AndroidWorks_00.png

  4. 다음 버튼을 눌러 계속합니다.

    AndroidWorks_01.png

  5. Android Works 를 다운로드하고 설치할 위치를 설정한 뒤 다음 버튼을 누릅니다.

    AndroidWorks_02.png

    이 위치는 기본 위치로 놔둬도 전혀 상관 없습니다.

  6. AndroidWorks1R1 설치중인지 확인한 뒤 다음 버튼을 누릅니다.

    AndroidWorks_03.png

  7. 체크박스를 클릭하고, 라이선스 조항에 동의하면 모두 수락 을 누른 뒤 수락 버튼을 누릅니다.

    AndroidWorks_04.png

  8. 필수 Android Works 툴의 다운로드 및 설치 진행상황이 표시되는 창이 새로 뜹니다.

    이 부분의 완료를 위해서는 인터넷 연결이 필요합니다. 그 인터넷 연결 속도에 따라 몇 분에서 몇 시간까지 걸릴 수 있습니다.

    AndroidWorks_06.png

  9. 필수 툴의 다운로드 및 설치가 전부 끝나면 다음 창이 표시됩니다. OK 버튼을 눌러 설치 프로세스를 계속합니다.

    AndroidWorks_08.png

  10. 이제 완료 버튼을 눌러 Android Works 설치를 완료합니다.

    AndroidWorks_09.png

  11. 마지막으로  버튼을 눌러 컴퓨터를 재시작합니다.

    AndroidWorks_10.png

    GitHub 에서 UE4 를 다운로드한 경우, Android Works 가 설치를 완료하면 환경 변수 설정을 위해 PC 또는 맥을 재시작하고 Setup.bat 파일을 한 번 더 실행하여 필수 안드로이드 파일을 다운로드합니다.



http://docs.unrealengine.com/latest/KOR/Platforms/Android/GettingStarted/2/index.html



2. 안드로이드 디바이스 셋업

  • SHARE:

언리얼 엔진

Android Works 가 설치되었으니 안드로이드 디바이스를 개발에 사용할 수 있도록 구성해 줄 차례입니다. 여기서는 UE4 프로젝트를 실행하는 데 안드로이드 디바이스를 사용할 수 있도록 구성하기 위해 알아야 하는 모든 것에 대해 다루겠습니다.

운영 체제 선택

Windows

Mac OS

  1. USB 를 통해 개발 PC 에 안드로이드 디바이스를 연결합니다.

  2. 디바이스 드라이버 소프트웨어가 자동으로 설치될 수도 있지만, 그렇지 않은 경우 Android's OEM USB Driver 페이지를 방문하여 드라이버 설치 링크 및 추가 정보를 확인할 수 있습니다.

  3. 안드로이드 디바이스에서 Settings 어플리케이션을 엽니다.

  4. Developer Options 메뉴에서 Developer Options 를 탭합니다.

    이 항목이 보이지 않는 경우, 디바이스의 Developer Options 활성화가 필요합니다. 자세한 내용은 Android's Using Hardware Devices 페이지를 참고하세요.

  5. 화면 스크롤을 내려 About Phone 을 선택합니다. 안드로이드 디바이스에 따라 About Device, About Tablet, About Shield 옵션이 대신 나타날 수도 있습니다.

    주: 신형 안드로이드 버전의 경우 More 부분에 있을 수도 있습니다.

  6. Build Number 를 7 회 탭하여 개발자 모드를 활성화시킵니다.

    Enable_Dev_Mode.png

  7. 처음 몇 번 탭하고 나면 You are now # steps away from becoming a developer. 메시지가 뜰 것입니다.

  8. 개발자 모드가 활성화되면 아래와 비슷한 성공 메시지가 화면에 뜰 것입니다.

    Dev_Mode_Active.png

  9. Settings 메뉴로 되돌아가 사용가능해진 Developer Options 를 선택합니다.

    Dev_Options_Enabled.png

  10. Developer Options 메뉴에서 USB 디버깅을 탭하여 켭니다.

    Enable_USB_Debugging.png

  11. 묻는 창이 뜨면 OK 를 선택하여 USB 디버깅을 켭니다.

    Enable_USB_Debugging_Warning.png

  12. USB 디버깅 활성화 여부는 그 옆의 체크박스에 초록색 체크표시가 있는 것을 보고 알 수 있습니다.

    USB_Debugging_Enabled.png

  13. USB 에서 안드로이드 디바이스를 뽑은 다음 바로 다시 꽂습니다. 디바이스를 PC 에서 인식한 이후 안드로이드 디바이스에 이 PC 와의 통신을 허용하겠냐는 메시지가 뜹니다. 이 컴퓨터 항상 허용 이라는 체크박스를 누른 다음 OK 버튼을 누릅니다.

    PC_RSA_Fingerprint.png

  14. 디바이스 셋업이 제대로 되었는지 확인하기 위해, 윈도우+R 키를 눌러 실행 창에 cmd 라 입력합니다.

    Windows_Run_Command.png

  15. cmd 창에 adb devices 라 입력하면 PC 에 연결된 모든 디바이스를 확인할 수 있습니다.

    ADB_Devices.png

    adb devices 명령을 입력한 후에도 디바이스가 보이지 않는다면, PC 에서 해볼 수 있는 방법은 다음과 같습니다.

    • 디바이스가 나열은 되어 있으되 허가되지 않은 것으로 나타나는 경우, 디바이스에서 PC 승인을 하도록 해 줘야 함을 나타냅니다.

    • 디바이스가 나타나지 않으면 연결을 해제한 후 다시 연결해야 할 수도 있습니다.

    • Always allow 체크박스는 체크해 두는 것이 좋습니다.

    • 어떤 경우에는 제대로 환경설정된 디바이스도 Camera (PTP) 가 아닌 Media Device (MTP) 로 연결된 경우 나타나지 않을 수도 있습니다. 이 때 adb devices 아래 디바이스가 전혀 나타나지 않는 경우 Camera (PTP) 옵션을 선택해 보세요.


http://docs.unrealengine.com/latest/KOR/Platforms/Android/GettingStarted/3/index.html


3. 프로젝트 생성

  • SHARE:

언리얼 엔진

여기서는 안드로이드로의 디플로이를 테스트하는 데 사용할 프로젝트를 새로 만들겠습니다. 생성할 프로젝트는 블루프린트 삼인칭 템플릿을 사용하는 블루프린트 기반 프로젝트입니다.

  1. 언리얼 프로젝트 브라우저 에서 다음 옵션으로 블루프린트 기반 프로젝트를 새로 만듭니다.

    • 삼인칭 템플릿 사용

    • 타겟 하드웨어는 모바일 / 태블릿

    • 그래픽 레벨은 스케일가능 3D 또는 2D

    • 시작용 콘텐츠 비포함

    • 프로젝트 이름은 AndroidProject

new_android_project.png

이 예제에는 블루프린트 기반 프로젝트를 선택했지만, C++ 든 블루프린트든 어떤 유형의 프로젝트를 사용해서 안드로이드 디바이스에 패키징 및 디플로이 가능합니다.



4. 레벨 디플로이

  • SHARE:

언리얼 엔진

여기서는 작업중인 프로젝트의 레벨 하나를 안드로이드 디바이스에 디플로이하여 빠르게 테스트해 보는 방법을 살펴보겠습니다.

이번 섹션에서는 안드로이드 디바이스가 개발 PC 의 USB 를 통해 연결되어 있어야 합니다. 이미 연결하지 않은 경우, 먼저 연결한 뒤 진행해 주시기 바랍니다.

안드로이드 디바이스에 레벨을 디플로이하려면 먼저 안드로이드 디바이스가 지원하는 텍스처 포맷을 결정해야 합니다. 왜냐면 각기 다른 안드로이드 디바이스마다 정상 작동을 위해서는 각기 다른 텍스처 포맷이 필요하기 때문입니다. 어느 안드로이드 기반 디바이스에 어느 텍스처 포맷이 맞는지는 다음 표와 같습니다.

포맷설명
DXT데스크탑 컴퓨터에서 사용되는 방식으로, Tegra 기반 디바이스에도 사용됩니다.
ATCQualcomm Snapdragon 기반 디바이스에 사용됩니다.
PVRImgTec PowerVR 기반 디바이스에 사용됩니다.
ETC1모든 디바이스에 지원되지만, 알파 채널이 있는 텍스처를 지원하지 않으므로, 텍스처가 압축되지 않아 게임의 다운로드 크기가 커지고 실행시간 메모리를 더욱 많이 사용합니다.
ETC2MALI 기반 디바이스 등에 사용됩니다.

어떤 텍스처 포맷을 사용해야 하는지 불확실하거나 디바이스가 지원하는 것이 무엇인지 모르겠는 경우, 게임 실행 후 다음과 같은 작업을 통해 알 수 있습니다.

  1. 화면을 네 손가락으로 한 번에 터치하면 대화창이 뜹니다.

  2. 이 대화창은 보통 (stat fps 같은) 콘솔 명령을 입력하는 데 사용되나, 디바이스가 지원하는 포맷을 표시해 주기도 합니다.

  3. 그 목록을 확인했으면, 그를 통해 디플로이/패키징시 보다 이상적인 유형을 선택할 수 있습니다.

Available_Texture_Formats.png

  1. 안드로이드 기반 디바이스에서 현재 레벨을 테스트하기 위해서는 먼저 테스트하고자 하는 레벨을 열어야 합니다. 이 예제에서는 지난 단계에서 생성한 블루프린트 기반 프로젝트의 ThirdPersonExampleMap 레벨을 사용하겠습니다.

    Correct_Level_Open.png

  2. ThirdPersonExampleMap 을 연 채로 메인 툴바 로 이동한 뒤 실행 아이콘 옆의 작은 삼각형을 클릭하면 추가 옵션이 표시됩니다.

    Level_Deploy_Options.png

  3. 디바이스 섹션 아래 실행 메뉴에서 목록의 안드로이드 디바이스를 클릭하여 선택합니다.

    launch_rightformat.png

  4. 디바이스에서 레벨이 실행되는 도중 그 진행상황이 화면 우하단 구석에 표시됩니다. 프로젝트가 디바이스에 성공적으로 디플로이되면 알림창이 뜹니다.

  5. 쿠킹 및 실행 프로세스가 완료된 후, 게임이 자동으로 디바이스에 뜨며, 앱 드로어에서도 접근할 수 있습니다.

    Deployed_Project_Android.png




5. 게임 패키징

  • SHARE:
언리얼 엔진

다른 사람과 프로젝트를 공유하거나 디지털 스토어에 올려 판매하기 위해서는, 프로젝트를 패키징해야 합니다. 여기서는 완성된 프로젝트를 UE4 내에서 배포용으로 패키징하는 방법을 살펴보겠습니다.

운영 체제 선택

Windows

Mac OS

현재 이 게임을 테스트중이기에 Development 로 패키징하고 있으나, 게임이 완성되면 패키지 프로젝트 메뉴에서 빌드 환경설정 옵션에 커서를 올려 Shipping 으로 패키징하면 됩니다.

  1. 파일 메뉴에서 패키지 프로젝트 > 안드로이드 로 가서 패키징하고자 하는 텍스처 포맷을 선택합니다. 이번 예제에서는 모든 디바이스에 지원되는 안드로이드 ETC1 을 선택하겠습니다.

    package_menu.png

    각기 다른 디바이스마다 실행되는 하드웨어에 따라 각기 다른 텍스처 포맷을 지원합니다. 다양한 포맷에 대한 세부적인 분석에 대해서는 안드로이드 개발 참고서 문서를 참고하시기 바랍니다.

  2. 그러면 패키징된 게임을 저장할 위치를 묻는 창이 뜹니다. 지금은 데스크탑에 새 폴더를 만들어 그 위치에 프로젝트를 저장하도록 하겠습니다.

    package_folder.png

  3. 프로젝트가 패키징되는 동안 우하단 구석에 뜨는 패키징 메시지로 패킹 프로세스 진행상황이 표시됩니다.

    package_toast.png

  4. 패키징에 성공하면, 패키징 완료 메시지가 에디터 우하단 구석에 뜹니다.

    Packageing_Completed.png

  5. 2 단계에서 생성된 폴더로 이동합니다. 이 폴더에 보면 패키징시 선택한 텍스처 유형에 맞는 폴더가 새로 생겨있을 것입니다. 이번 예제에서 그 폴더 이름은 Android_ETC1 입니다.

    Android_ECT1_Folder.png

  6. Android_ETC1 폴더를 열고 Install[ProjectName]Development.bat 뱃치 파일을 실행하여 프로젝트를 안드로이드 디바이스에 설치합니다.

    Install_Bat.png

    안드로이드 디바이스는 USB 를 통해 개발 PC 에 연결되어 있어야 프로젝트가 디바이스에 디플로이됩니다. .BAT 파일 실행시 디바이스가 연결되지 않은 경우 아무런 작업도 하지 않습니다.

  7. .BAT 파일 작업이 완료되면 안드로이드 디바이스에서 프로젝트를 사용할 준비가 된 것이 보일 것입니다.

    Game_On_Phone.png



http://docs.unrealengine.com/latest/KOR/Platforms/Android/GettingStarted/6/index.html


6. 직접 해보기

  • SHARE:

언리얼 엔진

여기서는 안드로이드 디바이스에 UE4 프로젝트를 디플로이시키는 방법을 연습하고 가다듬을 수 있도록 직접 해볼 수 있는 몇 가지 것들에 대해 다루겠습니다.

UE4 프로젝트를 패키징하고 안드로이드 디바이스에서 테스팅하기 위한 준비를 마쳤으니, 이번 퀵스타트 가이드에서 배운 것을 토대로 다음과 같은 작업을 해 보세요.

  • 기본 템플릿 중 하나를 사용해서 새 프로젝트를 만든 다음 그 프로젝트가 안드로이드 디바이스에서 실행되도록 만듭니다.

  • 다양한 안드로이드 텍스처 포맷을 사용해서 프로젝트를 패키징해 보고, 대상 안드로이드 디바이스에 어느 것이 잘 맞는지 확인합니다.

  • 패키징된 파일 크기를 확인한 다음 APK 패키지 크기 줄이기 문서를 통해 크기 압축을 시도해 봅니다.

  • 삼성 기어 VR 디버깅 문서를 참고하여 무선 네트워크를 통해 안드로이드 디바이스에 프로젝트를 디플로이해 봅니다.

다음 링크는 어떤 안드로이드 디바이스가 UE4 에 적합한가서부터 모바일 디바이스를 대상으로 한 콘텐츠 제작시 고려할 사항까지 그 모든 것에 대한 도움이 될 수 있습니다. 아직 둘러보지 않으셨다면 매우 귀중한 정보가 넘쳐흐로고 있으니 한 번 둘러보실 것을 강력 추천합니다.

디바이스 호환성과 퍼포먼스 관련 상세 정보입니다:

모바일 디바이스용 게임 콘텐츠 및 레벨 디자인 관련 상세 정보입니다:

모바일 프리뷰어 를 사용하면 디바이스에 디플로이하지 않고도 모바일 게임을 미리볼 수 있습니다.

반응형
반응형

Emitter 를 스폰한 다음 Auto Destroy 옵션이 먹지 않는 경우는 이펙트가 무한 loop 를 돌게 될때임


Cascade(이펙트 툴) 에서 Duration 을 0 이 아닌 다른 값으로 주면 그 횟수 만큼 돌고 끝남


0 이면 무한 loop



[Bug] Spawn Emitter at Location does not auto destroy

2

So, been creating a projectile today and I wanted to spawn an emitter at the point where the projectile hit. Well, I used spawn emitter at location, and it did spawn an emitter, but even though I checked the little auto destroy box, the emitters never go away. The emitters should only last for about 3 seconds before they go through a full cycle/lifetime. Am I doing something wrong or is this really a bug?

Product Version: Not Selected
Tags:
more ▼

asked May 28 '14 at 11:31 AM

Knobbynobbes gravatar image

Knobbynobbes 
116  21  31  33

iveytron gravatar image iveytron May 28 '14 at 11:48 AM

Is your emitter by chance set up to be looping? (Emitter loops set to 0) If so, I don't believe the emitter ever "ends", meaning it wont know when to destroy itself.


1 answer:sort voted first 
3

It may be to do with the setup of your particle system - if a particle system never completes (i.e it is looping), the emitter is never finished and therefore never destroyed.

What does your particle setup look like?

more ▼

answered May 28 '14 at 11:47 AM

ambershee gravatar image

ambershee ♦ 
478  13  21  37

Knobbynobbes gravatar image Knobbynobbes May 28 '14 at 6:18 PM
1

Yup, it seems that my emitters were all set to loop = 0. setting that at 1 fixed it. thx all!

evillego6 gravatar image evillego6 Jun 11 '14 at 8:46 AM

Could you possibly tell me where you can set the loop property you're talking about? I can't find it anywhere.

ambershee gravatar image ambershee ♦ Jun 11 '14 at 8:49 AM
1

It's pretty easy to find.

Every emitter has it's own number of loops property in the require module.

evillego6 gravatar image evillego6 Jun 11 '14 at 9:22 AM Newest

Thank you. You're right, I should have seen that.





https://answers.unrealengine.com/questions/49128/bug-spawn-emitter-at-location-does-not-auto-destro.html

반응형
반응형

콜리전 개요

http://docs.unrealengine.com/latest/KOR/Engine/Physics/Collision/Overview/index.html

  • SHARE:

Collision Responses (콜리전 반응) 및 Trace Responses (트레이스 반응)은 언리얼 엔진 4 에서 콜리전 (충돌) 및 레이 캐스팅 (광선 투사) 실시간 처리를 위한 바탕을 이룹니다. 충돌 가능한 모든 오브젝트는 Object Type (오브젝트 유형)과 일련의 반응들을 통해 다른 모든 오브젝트 유형과 어떻게 상호작용하는지를 정의합니다. 콜리전(충돌) 또는 오버랩(겹침) 이벤트가 발생하면, 그에 관련된 양쪽 (또는 모든) 오브젝트는 서로 막을지, 겹칠지, 아니면 무시할지 영향을 주고받도록 설정할 수 있습니다.

트레이스 반응 작동방식도 기본적으로 같으나, 한 가지 차이라면 트레이스 (레이 캐스트) 자체를 하나의 트레이스 반응 유형으로 설정하여, 액터가 그 트레이스 반응에 따라 트레이스를 막거나 무시하도록 할 수 있습니다.


상호작용

콜리전 처리 방식에 있어 유념해야 할 규칙이 몇 가지 있습니다:

  • Blocking (막음)은 Block (막음)으로 설정된 두 (또는 그 이상의) 액터 사이에 자연적으로 발생합니다. 하지만 Simulation Generates Hit Events (시뮬레이션에서 히트 이벤트 생성) 옵션을 켜 줘야 Event Hit 를 실행할 수 있는데, 이는 블루프린트, 디스트럭터블 액터, 트리거 등에서 사용됩니다.

  • 액터를 Overlap (겹침)으로 설정하면 마치 서로 Ignore (무시)하는 것처럼 보이며, 실제로 Generate Overlap Events (오버랩 이벤트 생성) 옵션이 없으면 기본적으로 같습니다.

  • 둘 이상의 시뮬레이션 오브젝트가 서로를 막도록 하려면, 그 각각의 유형에 대해 막음 설정되어 있어야 합니다.

  • 둘 이상의 시뮬레이션 오브젝트에 대해, 하나가 오브젝트 겹침 설정되어 있고, 두 번째 오브젝트가 다른 것을 막음 설정되어 있는 경우, 겹침은 발생하나 막음은 발생하지 않습니다.

  • 오버랩 이벤트는 한 오브젝트가 다른 것을 막는 경우에도 발생 가능한데, 특히나 고속 이동인 경우 좋습니다.

    • 한 오브젝트가 충돌 및 겹침 이벤트 둘 다 갖는 것은 좋지 않습니다. 가능은 하지만, 수동 처리가 필요한 부분이 많습니다.

  • 한 오브젝트가 무시 설정되어 있고, 다른 것은 겹침 설정된 경우, 겹침 이벤트는 발생하지 않습니다.

레벨 테스트나 월드를 둘러보기 위한 목적으로는:

  • 기본 에디터에서 플레이 카메라는 폰입니다. 그래서 폰을 막는 것으로 설정된 것이면 막힙니다.

  • 에디터에서 시뮬레이트 카메라는, 빙의하기 전이면 폰은 아닙니다. 자유롭게 모든 것을 뚫고 들어갈 수 있으며, 충돌이나 겹침 이벤트가 생성되지 않습니다.


반응형
반응형

Collision Presets (콜리전 프리셋)

https://docs.unrealengine.com/latest/KOR/Engine/Physics/Collision/Reference/index.html


프로퍼티

아래는 피직스 바디 (바디 인스턴스)의 콜리전 프로퍼티 내 하위 카테고리인 콜리전 프리셋의 프로퍼티입니다.

collProp.png


property

spacer.png설명
Collision Presets콜리전 프리셋 -

기본 콜리전 프로파일과 프로젝트 세팅 -> 엔진 -> 콜리전 -> 프리셋 에 만들어 둔 것은 여기에 나타납니다.

프로퍼티spacer.png설명
Custom...커스텀 - 이 인스턴스에 대한 모든 커스텀 콜리전 세팅을 설정합니다.
NoCollision콜리전 없음 - 충돌이 없습니다.
BlockAll모두 막음 - 기본적으로 모든 액터를 막는 WorldStatic 오브젝트입니다. 모든 새 커스텀 채널은 자체적인 기본 반응을 사용합니다.
OverlapAll모두 겹침 - 기본적으로 모든 액터에 겹치는 WorldStatic 오브젝트입니다. 모든 새 커스텀 채널은 자체적인 기본 반응을 사용합니다.
BlockAllDynamic모든 다이내믹 막음 - 기본적으로 모든 액터를 막는 WorldDynamic 오브젝트입니다. 모든 새 커스텀 채널은 자체적인 기본 반응을 사용합니다.
OverlapAllDynamic모든 다이내믹 겹침 - 모든 액터에 기본적으로 겹치는 WorldDynamic 오브젝트입니다. 모든 새 커스텀 채널은 자체적인 기본 반응을 사용합니다.
IngoreOnlyPawn폰만 무시 - 폰과 비히클을 무시하는 WorldDynamic 오브젝트입니다. 다른 모든 채널은 기본으로 설정됩니다.
OverlapOnlyPawn폰만 겹침 - 폰, 카메라, 비히클에 겹치는 WorldDynamic 오브젝트입니다. 다른 모든 채널은 기본으로 설정됩니다.
Pawn폰 - 폰 오브젝트입니다. 플레이가능 캐릭터나 AI 의 캡슐로 사용할 수 있습니다.
Spectator관람자 - WorldStatic 제외 다른 모든 액터를 무시하는 폰 오브젝트입니다.
CharacterMesh캐릭터 메시 - 캐릭터 메시에 사용되는 폰 오브젝트입니다. 다른 모든 채널은 기본으로 설정됩니다.
PhysicsActor피직스 액터 - 시뮬레이팅되는 액터입니다.
Destructible디스트럭터블 - 파괴가능 액터입니다.
InvisibleWall투명 벽 - 보이지 않는 WorldStatic 오브젝트입니다.
InvisibleWallDynamic투명 벽 다이내믹 - 보이지 않는 WorldDynamic 오브젝트입니다.
Trigger트리거 - 트리거에 사용되는 WorldDynamic 오브젝트입니다. 다른 모든 채널은 기본으로 설정됩니다.
Ragdoll래그돌 - 시뮬레이팅되는 스켈레탈 메시 컴포넌트입니다. 다른 모든 채널은 기본으로 설정됩니다.
Vehicle비히클 - Vehicle, WorldStatic, WorldDynamic 을 막는 비히클 오브젝트입니다. 다른 모든 채널은 기본으로 설정됩니다.
UIUI - 기본으로 모든 액터에 겹치는 WorldStatic 오브젝트입니다. 모든 새 커스텀 채널은 자체적인 기본 반응을 사용합니다.
Collision Enabled콜리전 켜짐 -

Collision Enabled 는 아래 네 가지 상태를 가질 수 있습니다.

프로퍼티spacer.png설명
No Collision콜리전 없음 - 이 바디에는 콜리전이 활성화되지 않습니다.
Query Only쿼리 전용 - 이 바디는 콜리전 쿼리(레이캐스트, 스윕, 오버랩)에만 사용됩니다.
Physics Only피직스 전용 - 이 바디는 피직스 콜리전에만 사용됩니다.
Collision Enabled콜리전 활성화 - 이 바디는 모든 콜리전(쿼리와 피직스 양쪽)과 상호작용합니다.
Object Type오브젝트 유형 -

Enum indicating what type of object this should be considered as when it moves.

임의의 설정이지만, 피직스 바디의 역할에 맞춰 설정해야 합니다.

프로퍼티spacer.png설명
WorldStatic월드 스태틱 - 이동하지 않는 액터에 사용합니다. 스태틱 메시 액터가 WorldStatic 유형을 갖는 액터의 좋은 예입니다.
WorldDynamic월드 다이내믹 - 애니메이션 또는 코드(키네마틱)의 영향 하에 움직이는 액터 유형에 쓰입니다. 리프트나 문이 WorldDynamic 액터의 좋은 예입니다.
Pawn폰 - 플레이어 제어 개체는 Pawn 유형이어야 합니다. 플레이어의 캐릭터가 폰 오브젝트 유형을 받는 좋은 예입니다.
PhysicsBody피직스 바디 - 피직스 시뮬레이션으로 인해 움직이게 되는 액터입니다.
Vehicle비히클 - 기본적으로 비히클은 이 유형을 받습니다.
Destructible디스트럭터블 - 기본적으로 디스트럭터블 메시가 이 유형을 받습니다.
Collision Responses콜리전 반응 -

이 피직스 바디가 다른 모든 유형의 트레이스 & 오브젝트 유형과 어떻게 상호작용하는지를 결정합니다. 기억할 것은, 최종 결과를 정의하는 것은 양쪽 피직스 바디 사이의 상호작용이라, 양쪽 피직스 바디의 오브젝트 유형과 콜리전 반응이 중요합니다.

iob.png

반응spacer.png설명
Ignore무시 - 다른 피직스 바디의 콜리전 반응과는 상관없이, 이 피직스 바디는 상호작용을 무시합니다.
Overlap겹침 - 다른 피직스 바디가 이 피직스 바디의 오브젝트 유형을 겹침 또는 막음으로 설정된 경우, 오버랩 이벤트 발생이 가능합니다.
Block막음 - 다른 피직스 바디가 이 피직스 바디의 오브젝트 유형을 막음으로 설정된 경우, 히트 이벤트 발생이 가능합니다.
Trace Responses트레이스 반응 -

트레이스 반응은 트레이스(광선 투사)에 사용되며, 그 예로 Line Trace by Channel 블루프린트 노드가 있습니다.

프로퍼티spacer.png설명
Visibility표시여부 - 일반적인 표시여부 테스트 채널입니다.
Camera카메라 - 주로 카메라에서 무언가로 트레이스할 때 사용됩니다.
Object Responses오브젝트 반응 -
프로퍼티spacer.png설명
WorldStatic월드 스태틱 - 이 피직스 바디가 WorldStatic 피직스 바디 오브젝트 유형과 상호작용할 때 어떻게 반응할 것인지 입니다.
WorldDynamic월드 다이내믹 - 이 피직스 바디가 WorldDynamic 피직스 바디 오브젝트 유형과 상호작용할 때 어떻게 반응할 것인지 입니다.
Pawn이 피직스 바디가 Pawnm 피직스 바디 오브젝트 유형과 상호작용할 때 어떻게 반응할 것인지 입니다.
PhysicsBody이 피직스 바디가 PhysicsBody 피직스 바디 오브젝트 유형과 상호작용할 때 어떻게 반응할 것인지 입니다.
Vehicle이 피직스 바디가 Vehicle 피직스 바디 오브젝트 유형과 상호작용할 때 어떻게 반응할 것인지 입니다.
Destructible이 피직스 바디가 Destructible 피직스 바디 오브젝트 유형과 상호작용할 때 어떻게 반응할 것인지 입니다.



반응형
반응형

Unreal Event

https://docs.unrealengine.com/latest/KOR/Engine/Blueprints/UserGuide/Events/index.html

이벤트

  • SHARE:

언리얼 엔진

Event 노드는 EventGraph 내 개별 네트워크의 실행을 시작시키기 위해 게임플레이 코드에서 호출되는 노드입니다. 게임 시작, 레벨 리셋, 대미지 적용 등 게임 내에서 벌어지는 이벤트에 반응하여 일련의 동작을 Blueprint 를 통해 할 수 있게 해 줍니다. Blueprint 에서 이러한 이벤트에 접근하여 새로운 함수성을 구현하거나 기본 함수성을 덮어쓰고 강화시킬 수 있습니다. 하나의 EventGraph 에서 사용할 수 있는 **Event* 의 수는, 각 유형별로 하나씩만 쓸 수 있기는 하지만, 몇 개든 사용할 수 있습니다.

Blueprint Class Events Expanded Level Blueprint Events Expanded

시퀀스에서 어느 한 이벤트는 딱 하나만 있을 수 있으며, 각 이벤트는 하나의 오브젝트만 실행할 수 있습니다. 한 이벤트에서 여러 동작을 발동시키려는 경우, 순차적으로 엮어 줘야 합니다.

마티네를 사용해서 시네마틱 시퀀스 재생 도중의 특정 시간에 이벤트를 발동시키는 방법은, 마티네로 블루프린트 프로퍼티 변경하기 문서를 참고하세요.

Event Level Reset

이 블루프린트 이벤트 노드는 레벨 블루프린트에서만 사용할 수 있습니다.

이 블루프린트 이벤트 노드는 서버에서만 실행됩니다. 싱글 플레이어 게임의 경우 로컬 클라이언트가 서버로 간주됩니다.

LevelReset.png

LevelReset (레벨 리셋) 이벤트는 레벨 재시작시 실행 신호를 보냅니다. 플레이어는 죽었는데 레벨은 다시 로드할 필요가 없는 게임 상황에서처럼, 레벨이 꼭 재시작될 때만 발동시킬 무언가가 있을 때 좋습니다.

LevelReset_Example.png

Event Actor Begin Overlap

BeginOverlap.png

다수의 조건이 동시에 만족했을 때 실행되는 이벤트입니다:

  • 액터간의 콜리전 반응은 오버랩을 허용해야 합니다.

  • 실행할 두 액터 모두 Generate Overlap Events 가 true 설정되어 있어야 합니다.

  • 마지막으로 두 액터의 콜리전이 겹치기 시작해야, 즉 둘 다 움직이거나, 하나가 다른 것에 겹쳐 생성되어야 합니다.

콜리전 관련 상세 정보: 콜리전 반응.

BeginOverlapEX.png

이 블루프린트 액터가 Player Actor 변수에 저장된 액터에 겹치는 경우, Counter 인티저 변수를 증가시킵니다.

항목설명

출력 핀

Other ActorActor - 이 블루프린트에 겹치는 액터입니다.

Event Actor End Overlap

EndOverlap.png

다수의 조건이 동시에 충족되면 발동되는 이벤트입니다:

  • 액터간의 콜리전 반응은 오버랩을 허용해야 합니다.

  • 이벤트를 실행할 두 액터 모두 Generate Overlap Events 가 true 설정되어 있어야 합니다.

  • 마지막으로 두 액터의 콜리전 겹치기가 중단되어야, 즉 서로 멀어지거나 하나가 소멸되어야 합니다.

콜리전 관련 상세 정보: 콜리전 반응.

EndOverlapEX.png

이 블루프린트 액터가 Player Actor 변수에 저장된 액터를 제외한 다른 액터에 더이상 겹치지 않으면, 겹쳤던 액터를 소멸시킵니다.

항목설명

출력 핀

Other ActorActor - 이 블루프린트에 겹치는 액터입니다.

Event Hit

EventHit.png

충돌에 관련된 액터 중 하나가 콜리전 세팅에 Simulation Generates Hit Events 옵션이 True 설정된 경우에만 실행되는 이벤트입니다.

Sweep 을 사용해서 무브먼트를 If you are creating movement using Sweeps, you will get this event even if you don't have the flag selected. This occurs as long as the Sweep stops you from moving past the blocking object.

항목설명

출력 핀

My CompPrimitiveComponent - 걸렸던 실행 액터 상의 컴포넌트입니다.
OtherActor - 콜리전에 관계된 다른 액터입니다.
Other CompPrimitiveComponent - 걸렸던 콜리전에 관계된 다른 액터상의 컴포넌트입니다.
Self MovedBoolean - (false 인 경우) 다른 오브젝트의 운동에서의 적중을 받는 데 사용됩니다. Hit Normal 와 Hit Impact Normal 의 방향은 다른 오브젝트에서 적중된 오브젝트에 대한 힘을 가리키도록 조정됩니다.
Hit LocationVector - 두 충돌 액터 사이의 접촉 위치입니다.
Hit NormalVector - 충돌의 방향입니다.
Normal ImpulseVector - 액터 충돌시의 힘입니다.
HitStruct HitResult - 한 번의 Hit 에 수집된 모든 데이터로, 이 결과를 분석 추출하여 개별 개별 데이터에 접근할 수 있습니다.

EventHitEX.png

이 예제에서, 이 블루프린트가 Hit _실행시, 임팩트 지점에서 폭발 이펙트를 스폰시킵니다.

Event Any Damage

이 블루프린트 이벤트 노드는 서버에서만 실행됩니다. 싱글 플레이어 게임의 경우 로컬 클라이언트가 서버로 간주됩니다.

AnyDamage.png

일반적인 대미지가 전해지면 전달되는 이벤트입니다. 잠수나 환경으로 인한 대미지처럼, 꼭 포인트 또는 래디얼 대미지일 필요는 없습니다.

항목설명

출력 핀

DamageFloat - 액터에 전달되는 대미지 양입니다.
Damage TypeObject 'DamageType' - 입히는 대미지에 대한 부가 데이터가 들어있는 오브젝트입니다.
Instigated ByActor - 대미지를 입힌 액터입니다. 총을 발사했거나 수류탄을 던져 대미지를 입힌 액터가 됩니다.
Damage CauserActor - 피해를 유발한 액터입니다. 총알 또는 폭발 같은 것이 됩니다.

여기서, 액터에 전해지는 대미지는 물에서 오고 있으며, 생명력을 깎으면서 화면에 경고를 출력합니다.

Event Point Damage

이 블루프린트 이벤트 노드는 서버에서만 실행됩니다. 싱글 플레이어 게임의 경우 로컬 클라이언트가 서버로 간주됩니다.

PointDamage.png

포인트 대미지는 프로젝타일, 즉시 적중 무기, 심지어 근접 무기로 입은 대미지를 나타내는 데 사용됩니다.

항목설명

출력 핀

DamageFloat - 액터에 전해지는 대미지 양입니다.
Damage TypeObject DamageType - 전해지는 대미지의 부가 데이터가 포함된 오브젝트입니다.
Hit LocationVector - 대미지가 적용되고 있는 위치를 나타냅니다.
Hit NormalVector - 콜리전 방향입니다.
Hit ComponentPrimitiveComponent - 걸린 실행 액터상의 컴포넌트입니다.
Bone NameName - 걸린 본의 이름입니다.
Shot from DirectionVector - 대미지를 입은 방향입니다.
Instigated ByActor - 대미지를 입힌 액터입니다. 총을 발사하거나 수류탄을 던져 피해를 입힌 액터를 나타냅니다.
Damage CauserActor - 피해를 유발한 액터입니다. 총알 또는 폭발 같은 것이 됩니다.

이 예제에서는, 대미지를 받으면 액터의 생명력에서 입은 피해량을 빼지만, 액터의 머리가 맞으면 액터의 생명력은 -1 로 설정됩니다.

Event Radial Damage

이 블루프린트 이벤트 노드는 서버에서만 실행됩니다. 싱글 플레이어 게임의 경우 로컬 클라이언트가 서버로 간주됩니다.

RadialDamage.png

이 시퀀스의 부모 액터가 방사형 대미지를 받을 때마다 Radial Damage 이벤트가 호출됩니다. 폭발형 대미지, 또는 간접적으로 유발된 대미지 처리에 좋습니다.

항목설명

출력 핀

Damage ReceivedFloat - 이벤트에서 받은 대미지 양입니다.
Damage TypeObject DamageType - 받은 대미지에 대한 부가 데이터가 들어있는 오브젝트입니다.
OriginVector - 대미지 진원지의 3D 스페이스 위치를 나타냅니다.
Hit InfoStruct HitResult - 한 번의 Hit 에 수집된 모든 데이터로, 이 결과를 분석 추출하여 개별 개별 데이터에 접근할 수 있습니다.
Instigated ByController - 대미지를 입힌 Controller (AI 또는 Player) 입니다.
Damage CauserActor - 대미지를 유발시킨 액터입니다. 총알, 로켓, 레이저, 또는 펀치를 날린 캐릭터가 될 수도 있습니다.

Event Actor Begin Cursor Over

BeginCursorOver.png

마우스 인터페이스 사용시, 마우스 커서가 액터에 올라가면 이 이벤트가 실행됩니다.

BeginCursorOverEX.png

이 액터 위로 마우스 커서가 지나가면, 다이내믹 머티리얼 인스턴스에 Highlight 라는 이름의 스칼라 파라미터를 1.0 으로 설정합니다.

Event Actor End Cursor Over

EndCursorOver.png

마우스 인터페이스 사용시, 마우스 커서가 액터를 벗어나면 이 이벤트가 실행됩니다.

EndCursorOverEX.png

Target Notification 에 저장된 액터를 게임에서 숨김으로 설정합니다.

Event Begin Play

BeginPlay.png

게임이 시작되면 모든 액터에 대해 발동되는 이벤트로, 게임 시작 이후 스폰되는 액터의 경우 바로 호출됩니다.

BeginPlayEX.png

플레이 시작이, 이 액터는 Health 를 1000, Score 를 0 으로 설정합니다.

Event End Play

EndPlay.png

액터가 더이상 월드에 존재하지 않게 되면 실행되는 이벤트입니다.

EndPlayEX.png

이 액터가 더이상 월드에 존재하지 않게 되면, 이벤트 호출 이유를 나타내는 스트링이 출력됩니다.

항목설명

출력 핀

End Play Reasonenum EEndPlayReason - Event End Play 가 호출된 이유를 나타내는 열거형입니다.

Event Destroyed

Destroyed.png

액터가 Destroy (소멸)되었을 때 실행되는 이벤트입니다.

DestroyedEX.png

이 예제에서, Score 변수는 Value 에 Score 를 더한 값으로 설정되고 있습니다.

Destroyed Event 는 앞으로 폐기될 예정입니다. Destroyed 함수 내 함수성은 EndPlay 함수로 통합되었습니다.

Event Tick

Tick.png

게임플레이 매 프레임마다 호출되는 단순한 이벤트입니다.

항목설명

출력 핀

Delta SecondsFloat - 프레임 사이에 경과되는 시간을 출력합니다.

TickEX.png

Delta Seconds 를 사용하여 카운트다운 타이머를 만든 다음 마지막 틱에 "Blast Off!" 라 로그에 출력하는 예제입니다.

Event Receive Draw HUD

HUD 클래스를 상속받은 블루프린트 클래스에서만 사용할 수 있는 이벤트입니다.

DrawHud.png

블루프린트에서 HUD 를 그릴 수 있도록 해 주는 특수 이벤트입니다. HUD 그리기 노드는 이 이벤트가 있어야 생성 가능합니다.

항목설명

출력 핀

Size XInt - 렌더링 창의 픽셀 단위 너비입니다.
Size YInt - 렌더링 창의 픽셀 단위 높이입니다.

렌더 창 가운데 클릭하면 뒤에 빨강 박스가 보이는 히트 박스 를 생성합니다.

Custom Event

Custom Event Node

Custom Event 노드는 별도의 작업방식을 가진 특수 노드입니다. 자세한 정보는 Custom Event 노드 문서를 참고하세요.


https://docs.unrealengine.com/latest/KOR/Engine/Blueprints/UserGuide/Events/index.html

반응형

+ Recent posts