Using UE 4.23.1
Basically, i'm following a very simple tutorial.
I've extended multiple base classes, and it seems in ANY of my extensions, the variables for all components (e.g., physics, collision, static mesh, etc) all reset EVERY TIME i do a full project compile.
For instance:
I've extended UStaticMeshComponent with custom functionality (TankTrack). I set the static mesh component, and adjust the Collision to "Simulation GEnerates Hit Events". This sticks, but as soon as i recompile the entire game, EVERYTHING is reverted to its original state. Help!!
Note: This happens on variables I declare (and make UPROPERTY(EditAnywhere)) as well as those defaulted to that component type (e.g., Physics, collision, etc)
Here is an example with a UActorComponent called "Grabber". Only the .h file should matter if the issue is with blueprint?
If i change maxPickupWeightKg, then recompile, the change does NOT persist.
// Fill out your copyright notice in the Description page of Project Settings.
#pragma once
#include "CoreMinimal.h"
#include "Components/ActorComponent.h"
#include "PhysicsEngine/PhysicsHandleComponent.h"
#include "Grabber.generated.h"
UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) )
class FPSExample_API UGrabber : public UActorComponent
{
GENERATED_BODY()
public:
// Sets default values for this component's properties
UGrabber();
protected:
// Called when the game starts
virtual void BeginPlay() override;
public:
// Called every frame
virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override;
/// Grabber functions and variables
UPROPERTY(EditAnywhere, Category = "Grab Setup")
float maxPickupWeightKg = 50.f;
};
.cpp Constructor is nothing fancy:
#include "Grabber.h"
#include "Math/UnrealMathUtility.h"
#include "CollisionQueryParams.h"
#include "Engine/EngineTypes.h"
#include "Engine/World.h"
#include "Components/ActorComponent.h"
#include "Components/PrimitiveComponent.h"
#include "GameFramework/Actor.h"
#define OUT
// Sets default values for this component's properties
UGrabber::UGrabber()
{
PrimaryComponentTick.bCanEverTick = true;
}
.
.
.
My Hierarchy for the FPS Blueprint this is on:
FirstPersonCharacter(self)
-
CapsuleComponent (This is where all the player meshes are)
-
CharacterMovement
PhysicsHandle
Grabber
Thanks !
I am placing this here because I've had the same issue. After many hours of testing and research, I found this answer in the unreal forums. I hope it helps.
https://forums.unrealengine.com/development-discussion/c-gameplay-programming/1530690-uproperty-value-keeps-resetting-on-every-compile?p=1651757#post1651757
Using 4.25.3 this has still not been fixed. My workaround is to create a child blueprint of the component and use that on my Actor. This way the property values do not get reset when compiling.
Related
I know this was aksed and answered a a couple of times e.g.
Solution-wide #define, Is There anyway to #define Constant on a Solution Basis? and How to define a constant globally in C# (like DEBUG).
But in my case I can not use any of the suggested methods:
I'm writing on different "modules" (or plugins if you want so) for UnityProjects (kind of a package providing a certain functionality). The idea is that a developer can load a certain "module" to use in his project by importing a UnityPackage with all scripts and resources in it.
But some of these modules themselves depend on other modules. So what I tried so far was having a class Constants in each module with seperated namespaces and preprocessor definitions.
Module A
#if !MODULE_A
#define MODULE_A // BUT I WOULD NEED THIS GLOBAL NOT ONLY HERE
#endif
namespace Module_A
{
public static class Constants
{
// some constants for this namespace here
}
}
Module B
#if !MODULE_B
#define MODULE_B // BUT I WOULD NEED THIS GLOBAL NOT ONLY HERE
#endif
#if !MODULE_A // WILL BE NOT DEFINED OFCOURSE SINCE #define IS NOT GLOBAL
#error Module A missing!
#else
namespace Module_B
{
public static class Constants
{
// some constants for this namespace here
}
// and other code that might require Module A
}
#endif
But ofcourse this cannot work like this since #defines are not global but only in the current file.
Problem
For this whole idea of modules and a simple "load your modules" I can not ask the user to first make changes to the project or solution settings how e.g. suggested by this answer but instead have to use only the (c#) resources that come imported with the UnityPackage (at least with my current know-how).
Is there any way to somehow set/define those constants for the entire Unity-Project by only importing the module's UnityPackage?
Edit:
I could find a solution for 1 definition in Unity using Assets/msc.rsp. But this still wouldn't work for multiple modules since they would have to write into the same file.
After a lot of searches I've finally been able to put together a surprisingly simple solution I'ld like to share with you:
InitializeOnLoad
Unity has an attribute [InitializeOnLoad]. It tells Unity to initialize according class as soon as
Unity is launched
After any re-compiling of scripts => also after importing a new unitypackage with scripts
static Constructor
In their Running Editor Code On Launch example, they show, how to combine this with a static constructor.
From static-constructors:
A static constructor is called automatically to initialize the class before the first instance is created or any static members are referenced.
While usually you still would have to create an instance of the class, the static constructor is "instanciated/executed" instantly when the class is initliazed, which we force using the [InitializeOnLoad] attribute.
Scripting Define Symbols
Further Unity actually has project wide defines in the PlayerSettings.
And the good part is: We also have access to them via scripting API:
PlayerSettings.GetScriptingDefineSymbolsForGroup
PlayerSettings.SetScriptingDefineSymbolsForGroup.
So what I did now is the following
Module A
This module has no dependencies but just defines a "global define" in the PlayerSettings. I placed this script somewhere e.g. in Assets/ModuleA/Editor (important is the last folder's name).
using System.Linq;
using UnityEditor;
namespace ModuleA
{
// Will be initialized on load or recompiling
[InitializeOnLoad]
public static class Startup
{
// static constructor is called as soon as class is initialized
static Startup()
{
#region Add Compiler Define
// Get the current defines
// returns a string like "DEFINE_1;DEFINE_2;DEFINE_3"
var defines = PlayerSettings.GetScriptingDefineSymbolsForGroup(EditorUserBuildSettings.selectedBuildTargetGroup);
// split into list just to check if my define is already there
var define = defines.Split(';').ToList();
if (!define.Contains("MODULE_A")
{
// if not there already add my define
defines += ";MODULE_A";
}
// and write back the new defines
PlayerSettings.SetScriptingDefineSymbolsForGroup(EditorUserBuildSettings.selectedBuildTargetGroup, defines);
#endregion
}
}
}
Module B
This module depends on Module A. So itself defines a "global define" (so later Modules can check their dependecies on Module B) but additionally it checks first, if Module A is imported. If Module A is missing, it prints an error to the Debug Console.
(You could as well throw a compiler error using #error SOME TEXT, but for some reason this is not capable of printing out the URL correctly so I decided for the Debug.LogError)
I placed this script somewhere e.g. in Assets/ModuleB/Editor
#if MODULE_A
using System.Linq;
#endif
using UnityEditor;
#if !MODULE_A
using UnityEngine;
#endif
namespace ModuleB
{
// Will be initialized on load or recompiling
[InitializeOnLoad]
public static class Startup
{
// static constructor is called as soon as class is initialized
static Startup()
{
#if !MODULE_A
Debug.LogErrorFormat("! Missing Module Dependency !" +
"\nThe module {0} depends on the module {1}." +
"\n\nDownload it from {2} \n",
"MODULE_B",
"MODULE_A",
"https://Some.page.where./to.find.it/MyModules/ModuleA.unitypackage"
);
#else
// Add Compiler Define
var defines = PlayerSettings.GetScriptingDefineSymbolsForGroup(EditorUserBuildSettings.selectedBuildTargetGroup);
var define = defines.Split(';').ToList();
if (!define.Contains("MODULE_B"))
{
defines += ";MODULE_B";
}
PlayerSettings.SetScriptingDefineSymbolsForGroup(EditorUserBuildSettings.selectedBuildTargetGroup, defines);
#endif
}
}
}
So later in other scripts of Module B I have two options (both do basically the same)
I can either check everywhere #if MODULE_A to check exactly the module this script relies on
or I can instead check #if MODULE_B to rather check with one line if all dependecies are fulfilled since otherwise I don't define MODULE_B.
On this way I can completely check all dependencies between certain modules which is awesome. The only two flaws I saw until now are:
We have to know how the define (e.g. MODULE_A) looks like for every module and if it is changed in the future it has to be changed in all depending modules as well
The "global define" isn't getting removed in case the module is deleted from the project
But well - which solution is perfect?
In general, the way I would solve this problem in C# is by defining a common set of interfaces that all your modules would contain. I think you can do this with Unity by placing the files from each module in the same location, thus allowing later installations to overwrite those same files (with, obviously, the same content). You would then put editor controls that expose properties to hold instances of those interfaces and then wire them up in the UI. You would test those properties for a value of null to determine which ones are missing.
Common.cs:
public interface IModuleA {}
public interface IModuleB {}
ModuleA.cs
public class ModuleA : IModuleA {}
ModuleB.cs
public class ModuleB : IModuleB
{
public IModuleA ModuleAInstance {get; set;}
private bool IsModuleAPresent()
{
return !ModuleAInstance == null;
}
}
The ideal way to solve it would be with a package manager and proper dependency injection, but doing that with Unity is not straightforward.
Unity3D has an interface like this, for any Component on a MonoBehavior you just do this:
public class LaraCroft:MonoBehaviour,IPointerDownHandler
{
public void OnPointerDown(PointerEventData data)
{
Debug.Log("With no other effort, this function is called
for you, by the Unity engine, every time someone touches
the glass of your iPhone or Android.");
}
You do not have to register, set a delegate or anything else. OnPointerDown (the only item in IPointerDownHandler) gets called for you every single time someone touches the screen.
Amazing!
Here's a similar interface I wrote ...
public interface ISingleFingerDownHandler
{
void OnSingleFingerDown();
}
Now, I want consumers to be able to do this...
public class LaraCroft:MonoBehaviour,ISingleFingerDownHandler
{
public void OnSingleFingerDown(PointerEventData data)
{
Debug.Log("this will get called every time
the screen is touched...");
}
Just to recap, using Unity's interface, the function gets called automatically with no further effort - the consumer does not have to register or anything else.
Sadly, I can achieve that only like this:
I write a "daemon" ..
public class ISingleFingerDaemon:MonoBehaviour
{
private ISingleFingerDownHandler needsUs = null;
// of course that would be a List,
// just one shown for simplicity in this example code
void Awake()
{
needsUs = GetComponent(typeof(ISingleFingerDownHandler))
as ISingleFingerDownHandler;
// of course, this could search the whole scene,
// just the local gameobject shown here for simplicity
}
... when something happens ...
if (needsUs != null) needsUs.OnSingleFingerDown(data);
}
And I get that daemon running somewhere.
If you're not a Unity user - what it does is looks around for and finds any of the ISingleFingerDownHandler consumers, keeps a list of them, and then appropriately calls OnPointerDown as needed. This works fine BUT
the consumer-programmer has to remember to "put the daemon somewhere" and get it running etc.
there are obvious anti-elegancies whenever you do something like this (in Unity or elsewhere), re efficiency, placement, etc etc
• this approach fails of course if a consumer comes in to existence at a time when the daemon is not searching for them (Unity's magic interfaces don't suffer this problem - they have more magic to deal with that)
(PS, I know how to write an automatic helper that places the daemon and so on: please do not reply in that vein, thanks!)
Indeed, obviously the developers at Unity have some system going on behind the scenes, which does all that beautifully because "their" interfaces are perfectly able to call all the needed calls, regardless of even items being created on the fly etc.
What's the best solution? Am I stuck with needing a daemon? And perhaps having to register?
(It would surely suck - indeed generally not be usable in typical Unity projects - to just make it a class to inherit from; that type of facility is naturally an interface.)
So to recap, Unity has this:
public class LaraCroft:MonoBehaviour,IPointerDownHandler
Surely there's a way for me to make a replacement, extension, for that...
public class LaraCroft:MonoBehaviour,ISuperiorPointerDownHandler
which can then be used the same way / which shares the magic qualities of that interface? I can do it fine, but only my making a daemon.
Update
Full solution for "ISingleFingerHandler" "IPinchHandler" and similar concepts in Unity is here: https://stackoverflow.com/a/40591301/294884
You say you don't want to do a daemon but that is exactly what Unity is doing. The StandaloneInputModule class that is automatically added when you add a UI component is that daemon.
What you can do is create a new class derived from one of the classes derived from BaseInputModule (likey PointerInputModule for your case) that can handle listening to trigger and raising your extra events then add that new class to the EventSystem object.
See the Unity manual section on the Event System for notes on how to create your custom events and more details on what the input module does.
I hate to answer my own questions, but the answer here is really:
You cannot. You do have to add a daemon.
But then, it's very much worth noting that
Indeed, Unity add a daemon - they just hide it a little.
The final absolutely critical point to understand is that:
Unity screwed-up: you cannot in fact inherit from their lovely StandAloneInputModule. This is a big mistake.
Unity's StandAloneInputModule and IPointerDownHandler family - are brilliant. But you can't inherit from them properly.
The fact is, you just have to inherit sideways from IPointerDownHandler. That's all there is to it.
The fact is you have to make your own daemon ("as if" it inherits from StandAloneInputModule) which actually just goes sideways from IPointerDownHandler family.
So the actual answer is (A) you have this
public interface ISingleFingerHandler
{
void OnSingleFingerDown (Vector2 position);
void OnSingleFingerUp (Vector2 position);
void OnSingleFingerDrag (Vector2 delta);
}
public class SingleFingerInputModule:MonoBehaviour,
IPointerDownHandler,IPointerUpHandler,IDragHandler
and (B) you do have to put that on a game object (it's a daemon), and then (C) it's just stupidly easy to finally handle pinches, etc.
public class YourFingerClass:MonoBehaviour, IPinchHandler
{
public void OnPinchZoom (float delta)
{
_processPinch(delta);
}
That's it!
Full production code for PinchInputModule ...
https://stackoverflow.com/a/40591301/294884
...which indeed inherits sideways from ("uses") IPointerDownHandler family.
My assumption is that MonoBehaviour runs a type check in ctor. Which is why you cannot use the ctor on those to avoid overriding that process. The common solution is that your interface would also require to implement a registering method (Vuforia does that for instance) so any new instance registers itself.
You could also extend MB class with your own MB system:
public class JoeMonoBehaviour : MonoBehaviour
{
protected virtual void Awake(){
Init();
}
private void Init(){
if(this is ISuperiorPointerDownHandler)
{
if(ISuperiorHandler.Instance != null){
ISuperiorHandlerInstance.RegisterPointerDownHandler(this as ISuperiorPointerDownHandler);
}
}
}
}
It does not have the magic of Unity but you cannot achieve the magic of Unity with MonoBehaviour. It require the sub class to make sure it calls the base.Awake() if overriding it.
You'd have to come up with your own side engine system to run your own engine logic. Not sure that'd be worth it.
Another solution is to create your own Instantiate:
namespace JoeBlowEngine{
public static GameObject Instantiate(GameObject prefab, Vector3 position, Quaternion rotation){
GameObject obj = (GameObject)Instantiate(prefab, position, rotation);
MonoBehaviour [] mbs = obj.GetComponentsInChildren<MonoBehaviour>(true); // I think it should also get all components on the parent object
foreach(MonoBehaviour mb in mbs){
CheckForSuperior(mb);
CheckForInferior(mb);
// so on...
}
return obj;
}
internal static CheckForSuperior(MonoBehaviour mb)
{
if(mb is SomeType) { SomeTypeHandler.Instance.Register(mb as SomeType); }
}
}
Now it look like you are doing some magic only with :
JoeBlowEngine.Instantiate(prefab, Vector3.zero, Quaternion.identity);
Good day! I just started studying Unreal Engine 4.12 for a week now. For your discretion - I have little knowledge in C++ programming. (Although I code using PHP so I understanding OOP to some extent) - and, I'm just getting a little familiar with visual scripting (blueprint).
What I want to do is change the players weapon by loading a new static mesh, that static mesh would be from a file path. There are currently no blueprint node that does that, many articles/forums are suggesting to build my own blueprint node.
I've done some research and I have found this: Dynamic Load Object C++ - and it is very promising - but, I have no knowledge of implementing it. I tried opening MyProject.h and pasted it there, I'm not sure what to do next - does it become a function? Or a blueprint node?
I 'am open to other suggestions (or directions) on how to achieve what I wanted. If there are other methods to achieve this, please share and educate me. Thank you very much!
Sincerely,
Chris
That static load is only helper. You can call C++ function only if you mark header of that function by UFUNCTION(...) macro. See this link.
So you can create your function and in it's implementation, you can call that helper. For example:
// Helpers.h
static FORCEINLINE UTexture2D* GetTexture2DByName(const FName& name) {
return LoadObjFromPath<UTexture2D>(name);
}
UFUNCTION(BlueprintCallable, Category = TCF2Helpers)
static UTexture2D* GetTexture2DForBlock(UBuildableBlockInfo* blockInfo);
// Helpers.cpp
UTexture2D* UHelpers::GetTexture2DForBlock(UBuildableBlockInfo* blockInfo)
{
if (!blockInfo)
return nullptr;
const FString baseFolder = TEXT("Texture2D'/Game/Textures/HUD/%s");
if (blockInfo->IsEmptyHand)
return GetTexture2DByName(*FString::Printf(*baseFolder, TEXT("EmptyHand.EmptyHand'")));
// another lines of implementation
}
But you need to ask yourself, if you really need to have it hardcoded. You can specify something like
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Widgets")
TSubclassOf<class UObjectWidget> wInGameMenu;
UPROPERTY(BlueprintReadOnly, Category = "Widgets")
UObjectWidget* InGameMenu;
where in override of function BeginPlay (this is due to creating widget on the fly) I have:
if (wInGameMenu)
{
InGameMenu = CreateWidget<UObjectWidget>(this, wInGameMenu);
}
UObjectWidget is successor of UUserWidget and my widgets (created in Editor) are reparented to have that widget as an inheretance base. I define which widget should be created on archetype of my object which holds it.
I'd implement it like that: (this may be changed if anyone tells me better way)
Create WeaponManager as ActorComponent
Create Weapon as SceneComponent (so you can attach it on skeleton socket)
Every Weapon will have it's own implementation based on same interface (maybe override of some functions defined in common ancestor?)
You can have multiple sub-childs (Energy weapon, shooting weapon etc) so you have correct inheritance and you avoid multiple implementation of same thing.
Every Weapon will define it's mesh and properties - again, if you hardcoded mesh path (it's OK since it is implementation), you can use code like that in the end of that list) or you can set that on archetype, if you'd like to code something in blueprint.
Then in WeaponManager you define all weapons (for example TArray<TSubclassOf<UWeapon>>
Every Weapon should define EWeaponType - enum af all weapons in game, so I can match defined weapons with it's type in TMap and then simply work with it on demand (show, hide, change weapon etc.) That type should be hardcoded to all implementations of weapons.
Load mesh in constructor:
//TerminalObject.h
UCLASS()
class TAUCETIF2_API ATerminalObject : public AStaticMeshActor
{
GENERATED_UCLASS_BODY()
};
// TerminalObject.cpp
ATerminalObject::ATerminalObject(const FObjectInitializer& ObjectInitializer)
: Super(ObjectInitializer)
{
static ConstructorHelpers::FObjectFinder<UStaticMesh> mesh(TEXT("StaticMesh'/Game/BuildingObjects/Meshes/terminal.terminal'"));
checkf(mesh.Succeeded(), TEXT("Failed to find mesh"));
auto mc = GetStaticMeshComponent();
checkf(mc, TEXT("Failed to find mesh component"));
mc->SetStaticMesh(mesh.Object);
}
I'm working on a project based on MSP430 microchip, using IAR compiler. Here is the simplified problem:
In my project I have 3 files:
In clock.h:
#define MCLK_8MHZ
void clk_init(void);
In clock.c:
#include "clock.h"
void clk_init(void)
{
#ifdef MCLK_8MHZ
#define delay_ms(x) __delay_cycles((long)(1000000*(double)x/1000.0))
#endif
#ifdef MCLK_12MHZ
...
#endif
}
In main.c:
#include "clock.h"
clk_init();
delay_ms(5);
And the compiler would say function "delay_ms" declared implicitly
I think it mistook the delay_ms() as a function instead of a macro. Sure I could define it as a real function. But I thought it would damage the accuracy of time controlling.
How to solve this problem?
Do you need quotes around your include in main.c like:
#include "clock.h"
?
If that is your only warning, it's something else.
I have an ATL/COM-based DLL, made using VC++ 6.0. It's used for various executables built using VB6.
I want to add some COM interfaces that will not be accessible via VB6, for the internal use of the DLL only. I want them to be COM interfaces rather than just C++ interfaces due to the fact that I'll be using them on objects which I only have COM interface references to (at the time of use).
That is, I don't know (at the time of use) that this pointer points to a CFoo; I just know that it points to an IFoo, where IFoo is a COM interface, published so that VB6 knows about it. From this IFoo pointer, I want to get an IFooInternal pointer, which every class that implements IFoo (not just CFoo) will implement. Moreover, I don't want IFooInternal to be accessible outside of the DLL itself; for example, I don't want IFooInternal to be accessible by VB6.
Any help with this would be greatly appreciated. Suggestions for alternate ways to accomplish the same overall goal would also be. Thanks in advance.
Answering my own question for the benefit of anyone who finds this thread in the future. However, please note that I am just guessing here, based on experimentation... it seems to work, at least in my specific situation, but I don't know.
First, in some appropriate header file (perhaps Hidden.h), put the following, replacing a newly generated UUID with a newly generated UUID:
#ifndef __Hidden_h__
#define __Hidden_h__
extern "C" {
#ifndef __IHidden_FWD_DEFINED__
#define __IHidden_FWD_DEFINED__
typedef interface IHidden IHidden;
#endif // __IHidden_FWD_DEFINED__
#ifndef __IHidden_INTERFACE_DEFINED__
#define __IHidden_INTERFACE_DEFINED__
EXTERN_C const IID IID_IHidden;
MIDL_INTERFACE("a newly generated UUID")
IHidden : public IUnknown
{
public:
virtual HRESULT STDMETHODCALLTYPE get_Something (
long __RPC_FAR *pVal ) = 0;
};
#endif // __IHidden_INTERFACE_DEFINED__
}
#endif // __Hidden_h__
For how to define other types of parameters and such for a function, refer to the C++ header that was generated by MIDL from your IDL file.
Next, in the header for any class that you want to implement this interface, add the interface to the class declaration:
class ATL_NO_VTABLE CBlah :
public CComObjectRootEx<CComSingleThreadModel>,
public CComCoClass<CBlah, &CLSID_CBlah>,
public ISupportErrorInfo,
public IConnectionPointContainerImpl<CBlah>,
public IBlah,
public IHidden
Also add it to the COM_MAP:
BEGIN_COM_MAP(CBlah)
COM_INTERFACE_ENTRY(IBlah)
COM_INTERFACE_ENTRY(ISupportErrorInfo)
COM_INTERFACE_ENTRY(IConnectionPointContainer)
COM_INTERFACE_ENTRY(IHidden)
END_COM_MAP
And from there on out it's just a matter of adding the standard C++ declarations and definitions of the interface's functions to the class:
public:
STDMETHOD(get_Something)(long *pVal);
(...)
STDMETHODIMP CBlah::get_Something(long *pVal)
{
if ( !pVal )
{
(error handling)
}
*pVal = 37;
return S_OK;
}
I hope this helps someone in the future. I also hope that it doesn't hurt me due to it being incorrect. As I said, though, it seems to work.
This doesn't sound like a problem that necessarily needs COM. Remember: If you get an unmarshalled IFoo* from COM, it is just a normal IFoo* – not some magic COM-Thing. So what you can do is simply define a normal C++-Interface IFooInternal and then dynamic_cast your IFoo* to that.