NodeFactooray

A general question, before i deepdive into the topic…

Let’s have a look at this class first:

We see a class with 2 Operations, Execute() and Widget(). DoVolume() is also an operation but it is only used inside this class 2 times.

What i want to achieve is having a node factory that produces nodes like this one. In this case, the description for creating the node would be:

  • name=“volume”
  • type=float

with this information i think i can build everything and with somewhat different info, other nodes can be produced.
think of another description that is name=“enabled” and type=toggle. That should produce a similar node but the widget wouldn’t be a slider but a toggle and the string in the Execute operation would be “enabled” instead of “volume”

in the end, i imagine having several descriptions producing several of such classes.

additionally to that, i want to create a Record from those descriptions, that could then look like:
image

so, again, here i would take the descriptions and generate according fields and operations with the according types from the descriptions: volume is a float, debug and reset are bools in this example.

Extra quest:
as you can see in the record, there’s an operation called SetVolume. This operation is used in the class from above in the DoVolume operation.


Well, there isn’t an explicit question about details, but i want to know if that all seems feasible and if there are certain things one has to keep an eye on?


I read the code provided by VL.RunwayML and Elias’ explanation, then did some first steps with it and that all looks clear and clean. The only thing is the Fragmented thing, which I believe I would need in my use case since I want to add several operations and not just one update operation and I want to use the operations as separate nodes later on… Is that correct?

1 Like

How many nodes are we talking about here? Are they all really the same? Or are there some subtle differences? In your screenshot you make use of Elementa - Elementa is patched, node factories must be written in C# (no way to access Elementa from there), so you’d need to outsource that part. You want a corresponding record for each generated node - that means generating a record from within C#. But that won’t be straightforward. More likely you’ll end up defining those records in C# manually, but then you’re kind of back at the beginning where you defined them in VL. So I’m really not sure this is the right approach. Maybe you can provide us with a bigger picture?

First of all, yes, this is a bit academic :) I could also patch all this with a patched factory and some interfaces but wanted to take the opportunity to have a look at the NodeFactory so i can learn the possibilities and limits.

One possible advantage of node generation would be that one could produce nicely named and categorized nodes.
image
With a patched system i would probably end up with a node like shown on the left, a nodegenerator could also create a node that is doing the exact same thing but is easier to digest for the end-user.
re: academic. that would be the only advantage that came to my mind in this usecase :)

The elementa from c# issue is one that also came to my mind. I was thinking about just adding some abstract WidgetDescription to the node and build the widgets afterwards from that description. But yes, this is a downside (and already a nice learning).

Regarding the record:
I want to have only one Record with all the elements’ values as a property with corresponding operations.

Yes, maybe a bigger picture describes it better:

imagine a config file like this:

<config>
    <tab>
        <float name="volume" default="0.5"/>
        <toggle name="debug" default="True"/>
    </tab>
</config>

that would lead to:

  • one record, containing 2 fields called volume (float32) and debug (boolean). both come with a Set and a Get operation: SetVolume, Volume, SetDebug and Debug.
  • 2 classes, one for volume and one for debug

Topic being code generation (one way or the other), let me suggest a different approach which hasn’t been tried yet, but since the introduction of editor extensions in 2021.4 definitely something we should keep an eye on more closely: generating patches using editor extensions.

Attached you’ll find a first sketch of a patch generator (it opens pressing “Alt+G”). It takes a super simplified description of a record (name and properties) and generates and places a corresponding record definition into the current canvas when you hit the bang button (note that you might need to switch the current tab before it reacts properly - we need to do some cleanup on our end regarding the API there).

This approach is of course very different to a node factory as the code generation happens at design time and not runtime. You as the developer use it as a tool which you can freely modify and adjust to your needs. There’d be of course many ways to actually do the patch generation, like sketched here from a simple model or using some kind of template system with replacement rules etc. I guess that highly depends on the actual use case. The challenge would be to build up a good easy to use node set to achieve these tasks.

Would that route be something you could consider? Could you apply it in your case?

VL.PatchGenerator.HDE.zip (35.6 KB)

3 Likes

Thanks a lot, that seems indeed even better and more versatile for my usecase!
Now I can patch records, classes and also opertions, yeah!

Also the ModelUtils are a very good entry point!

Only things (for now) i couldn’t find out myself are:

  • How to delete a node? (maybe Patch.RemoveParticipatingElement)
  • How to add the generated definition to the Definitions Patch? (e.g. how to get the Definition Patch of the currently opened document)
  • Can I even create a new document, add what I want to it and then save it?
  1. There should be RemoveChild, RemoveDecendent(s) etc. - probably look for it inside the ModelUtils.vl file, as I said, this needs a proper cleanup. Somehow hoping that with experiments like this we get a better idea what’s actually interesting and what’s not.
  2. From any model element you can get the document it’s in and from that one you can the canvas - which is the definition canvas. For example
    image
  3. Sure, for example
    image
3 Likes

This topic was automatically closed 365 days after the last reply. New replies are no longer allowed.