Unreal Engine 4 provides three specifiers to control the visibility and editability of an C++ class member exposed to Blueprint via UPROPERTY().
The documentation in the UE4 source code (see also UE4 wiki, UE4 documentation) says the following regarding editability:
For VisibleAnywhere, VisibleInstanceOnly, VisibleDefaultsOnly:
... cannot be edited at all.
For EditAnywhere, EditInstanceOnly, EditDefaultsOnly:
... can be edited ...
For BlueprintReadOnly:
... can be read by blueprints, but not modified.
and BlueprintReadWrite:
... can be read or written from a blueprint.
Questions:
Since the Visible* specifiers already restrict the usage to read only in Blueprints, why it is used in conjunction with BlueprintReadOnly? Isn't the second specifier superfluous? Example:
UPROPERTY(VisibleDefaultsOnly, BlueprintReadOnly)
UMyActorComponent* MyActorComponent;
Even more confusing is the usage of Edit* specifiers, which allow read and write in Blueprint, together with BlueprintReadOnly which restricts to read only in Blueprint. Aren't both specifiers opposing each other? Example:
UPROPERTY(EditAnywhere, BlueprintReadOnly)
UMyActorComponent* MyActorComponent;
Are the Visible*/Edit* specifiers valid in a different context than the BlueprintRead* specifiers? (the question is not about InstanceOnly (property windows for instances), DefaultsOnly (property windows for archetypes) and Anywhere (instances & archetypes))
tl;dr
Visible*/Edit* specifiers allow you (typically a game designer) to access/modify a variable directly in Blueprint Editor for quick configurations of class properties.
BlueprintRead* allow you to get/set the value of a variable in the Event Graph when you're doing Visual Scripting.
Explanation:
Some namings and explanations in the official documentation are indeed a little ambiguous, especially for beginners. In a nutshell, both Visible*/Edit* and BlueprintRead* expose a variable in a class to the Unreal Engine, but do different things. In fact, both question 2 and 3 can be answered via question 1. Let's see your question 1:
Since the Visible* specifiers already restrict the usage to read only in Blueprints, why it is used in conjunction with BlueprintReadOnly? Isn't the second specifier superfluous? Example:
UPROPERTY(VisibleDefaultsOnly, BlueprintReadOnly)
UMyActorComponent* MyActorComponent;
Here you're exposing an ActorComponent to the Engine. Here I'll explain a non-Component member variable first, because specifiers for Component "appears" to work differently from non-Component variables.
Suppose I have a TpsCharacter class for a Third Person Shooter character, which has the following 3 float variables:
// The zooming speed
UPROPERTY(EditDefaultsOnly, BlueprintReadOnly, Category = "Camera Zoom")
float ZoomSpeed;
// The FOV after zoom in
UPROPERTY(EditDefaultsOnly, BlueprintReadOnly, Category = "Camera Zoom")
float ZoomInFov;
// The default FOV
UPROPERTY(EditDefaultsOnly, BlueprintReadOnly, Category = "Camera Zoom")
float DefaultFov;
They're all specified as EditDefaultsOnly, which means that, after we create a Blueprint class called TpsCharacter_BP based on this C++ class and open this Blueprint, the values of these 3 variables are editable in the Details Panel for this Blueprint class, as shown in the picture:
Of course, by using Visible* specifiers, they are read-only (greyed out in the Details Panel) so you can't change their values.
Now let's get back to your MyActorComponent. Like I said, specifiers for Component works somewhat differently.
Component appear in the Components Panel together with its owner class in the Blueprint Editor instead of in Details Panel like a non-Component variable.
When you have neither Visible* nor Edit* specifiers for a Component, this Component itself will always appear in the Editor, but you can't access properties/variables inside this Component., and Details Panel for this Component will be empty.
Visible* specifier allows you to access the Component's properties via its Details Panel, just like accessing the 3 variables in my TpsCharacter_BP class. However, when you declare it as Edit*, the Details Panel will show wired settings, allowing you to modify the Pointer value of this Component rather than its contents. This is definitely one thing you should always avoid.
Rule of thumb for Component: NEVER declare them as Edit* because it allows you change the pointer value to point to other things; always do Visible*. For a non-Component object you're free to set Edit*.
Now it's much easier to understand BlueprintRead* specifier. Is it superfluous with the presence of Visible*? Is BlueprintReadOnly opposing Edit* specifiers? Absolutely no. Are they valid in different context? Yes. The BlueprintRead* specifier allows you to read/write a variable in the Event Graph in the Blueprint Editor, that is, when you're doing Blueprint Visual Scripting. For my TpsCharacter class above, since all 3 variables are declared BlueprintReadOnly, I can get their values inside the Event Graph as shown here:
You can do the same for your MyActorComponent. By using BlueprintReadWrite, you can also set the value for these variables in Event Graph.
I write such long answer to explain because they can really confuse beginners though they're actually simple concepts.
Related
Roald has written an excellent guide for the Twincat Eventlogger.
https://roald87.github.io/twincat/2020/11/03/twincat-eventlogger-plc-part.html
https://roald87.github.io/twincat/2021/01/20/twincat-eventlogger-hmi-part.html
For us this is exactly what we want, there is however 1 thing I haven't figured out. How to get the sourcename of the alarm in multiple languages in the HMI. params::sourceName gives the path in the software (example: MAIN.fbConveyor1.Cylinder1) This path can be customized when initializing the alarm (as Roald has shown). This doesn't work in my case, since I would like to define a generic alarm (example: "Cilinder not retracted within maximum time") that is instantiated multiple times.
I was thinking of using the source as a way to show the operator where the alarm occurs. We use this way (path) already for saving machine settings among other things. The machines we build are installed all over the world, so multilanguage is a must.
Beckhoff does support multilanguage alarm names (when defined), but the source is not defined, but dynamically generated.
Anyone have an idea how this problem can be solved?
If I understand your question correctly, then being able to parameterize the event text with information of the source of the problem should help you out.
If you define the event text as Cylinder {0} has not retracted in time. then you can add the arguments of that text during runtime.
IF bRaiseAlarm THEN
bRaiseAlarm := FALSE;
fbAlarm.ipArguments.Clear().AddString('Alice');
fbAlarm.Raise(0);
END_IF
However, since this also stated in the articles you mentioned, I am unsure if this would solve your problem.
'Alice' in this example, can be hard to localize. The following options come to my mind.
The string can be based on an ENUM. Enums can have textlist support, so if you add your translations there, that should allow multilingual output. However... this does require a lot of setup, placing translations inside your code, and making sure the PLC application is aware of the language that the parameter should use.
Use tags to mark the source device, as tags can be language invariant. It is not the most user-friendly method, but it could work for you. It would become something like: "Cylinder 'AA.1123' did not retract in time.". 'AA.1123' as a tag would have to be stored inside your PLC code as a string. You will have to trust that your operator can relate the tag back to the actual source.
Hopefully, this helped, or else please help me understand the problem better.
I have a need to go through a set of DICOM files and modify certain tags to be current with the data maintained in the database of an external system. I am looking to use GDCM. I am new to GDCM. A search through stack overflow posts demonstrates that the anonymizer class can be used to change tag values.
Generating a simple CT DICOM image using GDCM
My question is if this is the best use of the GDCM API or if there is a better approach for changing the values of individual tags such as patient name or accession number. I am unfamiliar with all of the API options but have a link to the API documentation. It looks like the DataElement SetValue member could be used, but it doesn't appear that there is a valid constructor for doing this in the Value class. Any assistance would appreciated. This is my current approach:
Anonymizer anon = new Anonymizer();
anon.SetFile(myFile);
anon.Replace(new Tag(0x0010, 0x0010), "BUGS^BUNNY");
Quite late, but maybe it would be still useful. You have not mention if you write in C++ or C#, but I assume the latter, as you do not use pointers. Generally, your approach is correct (unless you use System.IO.File instead of gdcm.File). The value (second parameter of Replace function) has to be a plain string so no special constructor is needed. You should probably start with doxygen documentation of gdcm, and there is especially one complete example. It is in C++, but there should be no problems with translation.
There are two different ways to pad dicom tags:
Anonymizer
gdcm::Anonymizer anon;
anon.SetFile(file);
anon.Replace(gdcm::Tag(0x0002, 0x0013), "Implementation Version Name");
//Implementation Version Name
DatsElement
gdcm::Attribute<0x0018, 0x0088> ss;
ss.SetValue(10.0);
ds.Insert(ss.GetAsDataElement());
I have a safety code which requires a variable and a copy of it.
I want to to hide the shadow redudant variable from the generated Doxygen docs, for instance, here a pseudo code:
uint16 Variable_1; //!< This variable I want to show up in the docs
uint16 Variable_2; // This one I don't want to show in the docs.
I could use conditional documenting (\cond) however, I need to marks or other approach per variable. As there are too much variables and they are spread in the code, oone mark per variable would be great!
If I uncheck the option "all entities" then all my local functions are hidden.
How do I hide only variables I want, like marking only "Variable_2"?
This is the problem:
Create a class and set the access to be private for some of the properties or methods.
Use the doc command for the created class. This will auto-generate documentation from your comments and show it in the built-in help browser.
doc classname
The problem is that documentation for the private properties and methods is not shown in the help browser. Is there any way to overcome this problem?
So I spent like 10 minutes using the debugger, jumping from one function to the next, tracing the execution path of a simple doc MyClass call.
Eventually it lead me to the following file:
fullfile(toolboxdir('matlab'),'helptools','+helpUtils','isAccessible.m')
This function is called during the process of generating documentation for a class to determine if the class elements (including methods, properties, and events) are publicly accessible and non-hidden. This information is used later on to "cull" the elements.
So if you are willing to modify MATLAB's internal functions, and you want the docs to always show all methods and properties regardless of their scope, just rewrite the function to say:
function b = isAccessible(classElement, elementKeyword)
b = true;
return
% ... some more code we'll never reach!
end
Of course, don't forget to make a backup of the file in case you changed your mind later :)
(on recent Windows, you'll need to perform this step with administrative privileges)
As a test, take the sample class defined in this page and run doc someClass. The result:
This behaviour is by design - the auto-generated documentation is intended for users of the class, who would only be able to access the public properties and methods.
There's no way that I'm aware of to change this behaviour.
You could try:
Use an alternative system of auto-generating documentation such as this from the MATLAB Central File Exchange (which I believe will document all properties, not just public).
Implement your own doc command. Your doc command should accept exactly the same inputs as the built-in doc command, detect if its inputs correspond to your class/methods/properties etc, and if so display their documentation, otherwise pass its inputs straight through to the built-in doc. Make sure your command is ahead of the built-in on the path.
Is there a way to find complete class info of an object in Lazarus. F1 doesn't work.
For example, I want to know the methods, events and properties of TSQLQuery. More specifically, I'm trying to find what constants I can use with the state property.
The docs I've found so far aren't really much help in this context.
I've also tried the menu that says 'object browser' but it simply points to the properites window.
TSQLQuery and its unit sqldb is not documented.
The state property however is from the base tdataset ancestor of sqlquery, and that IS documented.
Try typing TDatasetstate or tdataset and press F1
The best documentation is the source code. After you dropped a TSQLQuery on the form CTRL-click on the identifier "TSQLQuery" in the source editor. Lazarus will open the corresponding source file at the position where TSQLQuery is declared. Scroll down to the public methods or published properties to see everything you need. Identifiers usually are self-explanatory - the chm file often does not contain more info. And the source is always up-to-date.
You can do the same with any identifier. Depending on the Lazarus version you may land in the implementation part of the unit. In this case, just press SHIFT-CTRL Up/Down to go to the interface.