Geometry Nodes: allow naming geometry sets #114910

Open
Jacques Lucke wants to merge 7 commits from JacquesLucke/blender:geometry-names into main

When changing the target branch, be careful to rebase the branch in your fork to match. See documentation.
Member

This adds a new name member to the GeometrySet class. This name can be set with the new Set Geometry Name node. Currently, the name is only used in the spreadsheet when displaying instances.

The main purpose of this name is to help debugging in instance trees. However, in the future it may also be used when exporting instance trees or when creating separate objects from them.

Note, the name is not expected to be unique, it is fully in user control.

image

Naming geometries is necessary to make the spreadsheet more useful for instances, because currently the user has no information for which geometry is used by each instance.

We also want to use this name to improve the integration with grease pencil where sometimes layers become instances with the same name.

This adds a new `name` member to the `GeometrySet` class. This name can be set with the new `Set Geometry Name` node. Currently, the name is only used in the spreadsheet when displaying instances. The main purpose of this name is to help debugging in instance trees. However, in the future it may also be used when exporting instance trees or when creating separate objects from them. Note, the name is not expected to be unique, it is fully in user control. ![image](/attachments/2615a02d-257a-49e9-b3ad-3408379e986a) Naming geometries is necessary to make the spreadsheet more useful for instances, because currently the user has no information for which geometry is used by each instance. We also want to use this name to improve the [integration with grease pencil](https://code.blender.org/2023/11/geometry-nodes-workshop-november-2023/#grease-pencil-integration) where sometimes layers become instances with the same name.
229 KiB
Jacques Lucke added 1 commit 2023-11-15 12:12:21 +01:00
Jacques Lucke requested review from Lukas Tönne 2023-11-15 12:12:56 +01:00
Jacques Lucke requested review from Falk David 2023-11-15 12:12:56 +01:00
Jacques Lucke requested review from Simon Thommes 2023-11-15 12:12:57 +01:00
Jacques Lucke requested review from Hans Goudey 2023-11-15 12:12:57 +01:00
Hans Goudey approved these changes 2023-11-15 14:07:12 +01:00
Hans Goudey left a comment
Member

Code-wise this looks good.

Code-wise this looks good.
@ -137,2 +137,4 @@
public:
/**
* This is a user defined name for this geometry. It is not expected to be unique. It's main
Member
  • This is a -> A
  • It's main -> Its main
- `This is a` -> `A` - `It's main` -> `Its main`
JacquesLucke marked this conversation as resolved
Jacques Lucke added 1 commit 2023-11-15 16:31:53 +01:00
Falk David approved these changes 2023-11-16 10:57:47 +01:00
Jacques Lucke added 1 commit 2023-11-24 10:12:06 +01:00
Simon Thommes requested changes 2023-11-24 20:02:19 +01:00
Simon Thommes left a comment
Member

It did feel a bit weird to me initially to add a feature like this that is mainly for debugging in a way that it actually affects and integrates into your node-tree while the data cannot actually be retrieved and used in the node-tree itself. But after testing it for a bit, I do think it's fine.

Would be good to have some nodes around extracting this information into string attributes once those are a thing to make it more useful.

Some notes:

  • Would be nice if the Object/Collection Info nodes would also write the geometry name to the output. (I could have sworn this was already a thing somehow...)
  • To make it more useful in the Spreadsheet it would be great if the Name column could also be used for filtering

Both of these things are not very controversial I think, but would already leverage the simple initial version of this to a more useful capacity. Not sure how this looks on the implementation side though. Let me know if you think these things aren't realistic or should be a separate PR.

Name Propagation

I do have some thoughts regarding propagating this information in the node-tree. The way it works right now feels to me like it hasn't been specifically designed, but is rather a consequence of the way things are implemented, so I think we need to put a bit more thought into this.

At first I thought about handling the case for joining geometry. From the user perspective it's not immediately obvious to me why joining would lose the name, even if for example there is just one input, or all names of the inputs are the same.
I can generally understand why some operations might construct an entirely new geometry set and would thus clear the name, but to some degree this seems like more of an implementation detail. For the join node, I think, it is arguable since we have an explicit order of inputs, that is relevant for the way things are joined, already regarding index order, that the first input can be considered a main input that things are joined into. The same is the case also for the Separate Components node. So it wouldn't be unreasonable to me to propagate the name of the first geometry. Again it feels more like the reason for the fact that it does not propagate the name is more so the implementation of the node than a design decision. The Separate Geometry node for example does propagate the name to both ouputs.

In a broader scope when looking at entire node-trees, most operations right now do actually just propagate the name.
For nodes like Set Position that just operate on attribute data it is quite obvious why you would keep the name the same. But at the same time, when viewing both the geometry before and after the operation in the spreadsheet they would not be one geometry set, but still share the same name.
But even the 'conversion' nodes that reconstruct the data in a different geometry component like curve to mesh, points to volume, instance on points propagate the name at the moment. This can potentially result in a lot of confusing duplication of names for different geometry sets, since essentially any geometry that results from a named geometry set will inherit that name.
And since there is a difference in this propagation between nodes, I do feel like there is an additional source for confusion coming from the fact that some operations propagate the name while others don't. I think it's a lot more clear if we put the responsibility of clearing the name entirely on the user, rather than doing it in certain cases.

So the most hardcore approach would be to immediately clear the name with every geometry node, which I don't think is a good idea.
Another approach would be to differentiate the behavior based on specific nodes based on some rule. The way it's done right now though, shows me that this can seem quite arbitrary, since it immediately makes assumptions over the way that the user attaches semantic meaning to that operation, which we should generally avoid. (e.g. after attaching some buttons to a shirt, I might still want to call it a shirt)

My Conclusion

Personally I would propose to keep things broadly as they are, but indeed extend the name propagation to all nodes that have a geometry in and output that have a reaonable association, so including Join and Separate. (I'm not sure how many more examples there are that I'm missing)

Overall I think it is worth considering a way to identify unique geometry sets in the spreadsheet beyond the name to alleviate the resulting confusion. E.g. showing a hash in gray text next to the name that is actually unique. Potentially also identifying unmodified collection/object data would be useful.
I understand that this goes beyond the scope of this PR, but imo it's a crucial aspect to how we approach the propagation of this data to make sure unique geometries are still differentiable.

It did feel a bit weird to me initially to add a feature like this that is mainly for debugging in a way that it actually affects and integrates into your node-tree while the data cannot actually be retrieved and used in the node-tree itself. But after testing it for a bit, I do think it's fine. Would be good to have some nodes around extracting this information into string attributes once those are a thing to make it more useful. Some notes: - Would be nice if the `Object/Collection Info` nodes would also write the geometry name to the output. (I could have sworn this was already a thing somehow...) - To make it more useful in the Spreadsheet it would be great if the Name column could also be used for filtering Both of these things are not very controversial I think, but would already leverage the simple initial version of this to a more useful capacity. Not sure how this looks on the implementation side though. Let me know if you think these things aren't realistic or should be a separate PR. ### Name Propagation I do have some thoughts regarding propagating this information in the node-tree. The way it works right now feels to me like it hasn't been specifically designed, but is rather a consequence of the way things are implemented, so I think we need to put a bit more thought into this. At first I thought about handling the case for joining geometry. From the user perspective it's not immediately obvious to me why joining would lose the name, even if for example there is just one input, or all names of the inputs are the same. I can generally understand why some operations might construct an entirely new geometry set and would thus clear the name, but to some degree this seems like more of an implementation detail. For the join node, I think, it is arguable since we have an explicit order of inputs, that is relevant for the way things are joined, already regarding index order, that the first input can be considered a main input that things are joined into. The same is the case also for the `Separate Components` node. So it wouldn't be unreasonable to me to propagate the name of the first geometry. Again it feels more like the reason for the fact that it does not propagate the name is more so the implementation of the node than a design decision. The `Separate Geometry` node for example does propagate the name to both ouputs. In a broader scope when looking at entire node-trees, most operations right now do actually just propagate the name. For nodes like `Set Position` that just operate on attribute data it is quite obvious why you would keep the name the same. But at the same time, when viewing both the geometry before and after the operation in the spreadsheet they would not be one geometry set, but still share the same name. But even the 'conversion' nodes that reconstruct the data in a different geometry component like curve to mesh, points to volume, instance on points propagate the name at the moment. This can potentially result in a lot of confusing duplication of names for different geometry sets, since essentially any geometry that results from a named geometry set will inherit that name. And since there is a difference in this propagation between nodes, I do feel like there is an additional source for confusion coming from the fact that some operations propagate the name while others don't. I think it's a lot more clear if we put the responsibility of clearing the name entirely on the user, rather than doing it in certain cases. So the most hardcore approach would be to immediately clear the name with every geometry node, which I don't think is a good idea. Another approach would be to differentiate the behavior based on specific nodes based on some rule. The way it's done right now though, shows me that this can seem quite arbitrary, since it immediately makes assumptions over the way that the user attaches semantic meaning to that operation, which we should generally avoid. (e.g. after attaching some buttons to a shirt, I might still want to call it a shirt) ### My Conclusion Personally I would propose to keep things broadly as they are, but indeed extend the name propagation to all nodes that have a geometry in and output that have a reaonable association, so including Join and Separate. (I'm not sure how many more examples there are that I'm missing) Overall I think it is worth considering a way to identify unique geometry sets in the spreadsheet beyond the name to alleviate the resulting confusion. E.g. showing a hash in gray text next to the name that is actually unique. Potentially also identifying unmodified collection/object data would be useful. I understand that this goes beyond the scope of this PR, but imo it's a crucial aspect to how we approach the propagation of this data to make sure unique geometries are still differentiable.

I agree with the @SimonThommes ' issues and this is why i would be against this kind of meta data. On good terms, there should be no meta data at all.
Any changes to implementation and functionality of node will cause problems here.
My approach would be something like: meta data on links between sockets. If it is a Reroute or a group node, then the metadata passes through. In any other case, the metadata is lost. If the node group implementation can get the metadata intarnally (with matched name and type), then everything is working correctly. Otherwise the error message...
But i see that it seems that this is not what the goal of this PR is...

I agree with the @SimonThommes ' issues and this is why i would be against this kind of meta data. On good terms, there should be no meta data at all. Any changes to implementation and functionality of node will cause problems here. My approach would be something like: meta data on links between sockets. If it is a `Reroute` or a group node, then the metadata passes through. In any other case, the metadata is lost. If the node group implementation can get the metadata intarnally (with matched name and type), then everything is working correctly. Otherwise the error message... But i see that it seems that this is not what the goal of this PR is...
Contributor

That's a great concept.
Even without a complete sting attribute implementation, I can already think of several use cases that would benefit from it.
I tested it for a bit, and aside from what Simon has said, I want to raise another UX point.
I understand the implementation reason that the 'set geometry name' is defined on the geometry level, nonetheless, as I see it, the geometry name is only relevant within the context of multiple geometries or the instance domain.
IMO, even though the data itself is part of the geometry set, controlling it from the instance domain may be more intuitive.
For example, after importing a cube object as an instance, you may want to rename the geometry default name (which is working fine in my tests). In the current proposal, the way to achieve that would be to realize the object, set its name, and then convert it back into an instance.
And from another aspect, if someday you would add the option to access it, it would probably be from the instance domain and not from the geometry itself.

That's a great concept. Even without a complete sting attribute implementation, I can already think of several use cases that would benefit from it. I tested it for a bit, and aside from what Simon has said, I want to raise another UX point. I understand the implementation reason that the 'set geometry name' is defined on the geometry level, nonetheless, as I see it, the geometry name is only relevant within the context of multiple geometries or the instance domain. IMO, even though the data itself is part of the geometry set, controlling it from the instance domain may be more intuitive. For example, after importing a cube object as an instance, you may want to rename the geometry default name (which is working fine in my tests). In the current proposal, the way to achieve that would be to realize the object, set its name, and then convert it back into an instance. And from another aspect, if someday you would add the option to access it, it would probably be from the instance domain and not from the geometry itself.
Jacques Lucke added 3 commits 2023-11-29 16:16:16 +01:00
Author
Member

IMO, even though the data itself is part of the geometry set, controlling it from the instance domain may be more intuitive.

A problem is that the name is not really on the instance domain, because that would mean that different instances could have different names even if they reference the same geometry. I know you probably mean to store the name only in the InstanceReference. Technically, that can work, but it doesn't seem more convenient to me right now.

In the current proposal, the way to achieve that would be to realize the object, set its name, and then convert it back into an instance.

I don't quite understand the need to realize the object.

> IMO, even though the data itself is part of the geometry set, controlling it from the instance domain may be more intuitive. A problem is that the name is not really on the instance domain, because that would mean that different instances could have different names even if they reference the same geometry. I know you probably mean to store the name only in the `InstanceReference`. Technically, that can work, but it doesn't seem more convenient to me right now. > In the current proposal, the way to achieve that would be to realize the object, set its name, and then convert it back into an instance. I don't quite understand the need to realize the object.
Jacques Lucke requested review from Simon Thommes 2023-11-29 16:20:35 +01:00
Contributor

Actually, I don't really mind where it is stored, it can be kept on the geometry, but it should be accessed and changed from the instance domain. It's the same way that the 'Fill Curve' node can work on the instance domain, but it actually changes data at the geometry level.

A problem is that the name is not really on the instance domain, because that would mean that different instances could have different names even if they reference the same geometry.

It is like how two geometries can have the same name - in contrast to mesh data.

I know you probably mean to store the name only in the InstanceReference. Technically, that can work, but it doesn't seem more convenient to me right now.

My main point is not 'where should the name be stored' but 'where should the user interact with the geometry name' in an escense I am being deliberately ignorant of the technical side of this.

My ultimate question is: what is the purpose of the node? In what scenario and how would it be used?

As I see it, the purpose of the node is to distinguish and associate geometries in the context of other geometries, aka within the Instance domain.

As for the 'scenarios it may be used in', currently, the design is only about visualization and debugging, but still, even the debugging is only relvant within the context of the instance domain.
I can imagine many utility nodes that can read (selecting) and write (swapping instance reference) that could utilize the 'geometry name', of course, all of them would also be from the POV of instances.

I don't quite understand the need to realize the object.

I often find myself tossing around multiple instances stored on an object (with a geometry node). In my example above, the key part is that you import the object as an instance -> you'll have to realize it for changing its name.

How it is How I think it should be
image image
Actually, I don't really mind where it is stored, it can be kept on the geometry, but it should be accessed and changed from the instance domain. It's the same way that the 'Fill Curve' node can work on the instance domain, but it actually changes data at the geometry level. > A problem is that the name is not really on the instance domain, because that would mean that different instances could have different names even if they reference the same geometry. > It is like how two geometries can have the same name - in contrast to mesh data. >I know you probably mean to store the name only in the InstanceReference. Technically, that can work, but it doesn't seem more convenient to me right now. > My main point is not 'where should the name be stored' but 'where should the user interact with the geometry name' in an escense I am being deliberately ignorant of the technical side of this. My ultimate question is: what is the purpose of the node? In what scenario and how would it be used? As I see it, the purpose of the node is to distinguish and associate geometries in the context of other geometries, aka within the **Instance domain**. As for the 'scenarios it may be used in', currently, the design is only about visualization and debugging, but still, even the debugging is only relvant within the context of the instance domain. I can imagine many utility nodes that can read (selecting) and write (swapping instance reference) that could utilize the 'geometry name', of course, all of them would also be from the POV of instances. > I don't quite understand the need to realize the object. I often find myself tossing around multiple instances stored on an object (with a geometry node). In my example above, the key part is that you import the object **as an instance** -> you'll have to realize it for changing its name. |How it is|How I think it should be| |-|-| |![image](/attachments/0b3ef35c-bac8-4d8f-b1c0-8c046831baba)|![image](/attachments/aacdfd06-1042-48bf-a562-30342cce0cfe)|
Jacques Lucke added 1 commit 2024-03-13 11:22:10 +01:00
This pull request has changes conflicting with the target branch.
  • source/blender/blenkernel/BKE_node.hh

Checkout

From your project repository, check out a new branch and test the changes.
git fetch -u geometry-names:JacquesLucke-geometry-names
git checkout JacquesLucke-geometry-names
Sign in to join this conversation.
No Label
Interest
Alembic
Interest
Animation & Rigging
Interest
Asset Browser
Interest
Asset Browser Project Overview
Interest
Audio
Interest
Automated Testing
Interest
Blender Asset Bundle
Interest
BlendFile
Interest
Collada
Interest
Compatibility
Interest
Compositing
Interest
Core
Interest
Cycles
Interest
Dependency Graph
Interest
Development Management
Interest
EEVEE
Interest
EEVEE & Viewport
Interest
Freestyle
Interest
Geometry Nodes
Interest
Grease Pencil
Interest
ID Management
Interest
Images & Movies
Interest
Import Export
Interest
Line Art
Interest
Masking
Interest
Metal
Interest
Modeling
Interest
Modifiers
Interest
Motion Tracking
Interest
Nodes & Physics
Interest
OpenGL
Interest
Overlay
Interest
Overrides
Interest
Performance
Interest
Physics
Interest
Pipeline, Assets & IO
Interest
Platforms, Builds & Tests
Interest
Python API
Interest
Render & Cycles
Interest
Render Pipeline
Interest
Sculpt, Paint & Texture
Interest
Text Editor
Interest
Translations
Interest
Triaging
Interest
Undo
Interest
USD
Interest
User Interface
Interest
UV Editing
Interest
VFX & Video
Interest
Video Sequencer
Interest
Virtual Reality
Interest
Vulkan
Interest
Wayland
Interest
Workbench
Interest: X11
Legacy
Blender 2.8 Project
Legacy
Milestone 1: Basic, Local Asset Browser
Legacy
OpenGL Error
Meta
Good First Issue
Meta
Papercut
Meta
Retrospective
Meta
Security
Module
Animation & Rigging
Module
Core
Module
Development Management
Module
EEVEE & Viewport
Module
Grease Pencil
Module
Modeling
Module
Nodes & Physics
Module
Pipeline, Assets & IO
Module
Platforms, Builds & Tests
Module
Python API
Module
Render & Cycles
Module
Sculpt, Paint & Texture
Module
Triaging
Module
User Interface
Module
VFX & Video
Platform
FreeBSD
Platform
Linux
Platform
macOS
Platform
Windows
Priority
High
Priority
Low
Priority
Normal
Priority
Unbreak Now!
Status
Archived
Status
Confirmed
Status
Duplicate
Status
Needs Info from Developers
Status
Needs Information from User
Status
Needs Triage
Status
Resolved
Type
Bug
Type
Design
Type
Known Issue
Type
Patch
Type
Report
Type
To Do
No Milestone
No project
No Assignees
6 Participants
Notifications
Due Date
The due date is invalid or out of range. Please use the format 'yyyy-mm-dd'.

No due date set.

Dependencies

No dependencies set.

Reference: blender/blender#114910
No description provided.