getting the original state of a referenced node

368 views
Skip to first unread message

Enrico Losavio

unread,
Nov 18, 2015, 7:01:27 AM11/18/15
to Python Programming for Autodesk Maya
Hi Everyone,

I have a mesh referenced in my Maya file, and I need to get the difference (vertex position, or deltas) between the actual mesh and the original mesh.
I managed to get a list of the edits via the cmds.referenceQuery() command, but that returns only a list of MEL commands, and I can't do much with that data.
What I would like to do is to run a MFnMesh.getPoints() both on the mesh I have now and also on the mesh as it was before the edits.
One solution would be to read the mesh data, unload the reference, clear the edits, reload the reference and then read the mesh data again, but I predict problems.
The reference edits system in Maya is very powerful but also very weak and unstable, and I don't trust in loading and unloading edits without something breaking (un)expectedly.
I believe that this information must be saved somewhere in Maya's memory, but I really can't find a way to access it.
I looked into the the MFileIO class, but I couldn't find any function that matches my needs.
Obviously I googled it, but it's not something easy to research on the internet, so...

...does anyone have any idea how to do this?

Any advice is more than welcome.

# Enrico

Marcus Ottosson

unread,
Nov 18, 2015, 7:21:08 AM11/18/15
to python_in...@googlegroups.com

In short, query the inMesh attribute of the referenced mesh.

Here’s some theory behind that.

 ________________      ______________      _____________
|                |    |              |    |             |
| ReferencedMesh |----| SomeDeformer |----| VisibleMesh |
|________________|    |______________|    |_____________|

The referenced mesh will always be in your scene and will always be untouched, with one exception. The manual “edits” you make when pulling vertices by hand or script. The mesh will have an inMesh and outMesh attribute, the inMesh representing it’s original state and outMesh the point at which those edits have been applied.

Thus, if you query the inMesh of the referenced mesh, you should be getting the mesh exactly as it was at the time of being referenced.

Unless! Unless the mesh already had edits in it’s original scene, in which case those would become lost. In that case, and alternative to the above, I’d create a new reference temporarily, query that, and later discard it.


--
You received this message because you are subscribed to the Google Groups "Python Programming for Autodesk Maya" group.
To unsubscribe from this group and stop receiving emails from it, send an email to python_inside_m...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/python_inside_maya/811b9658-2558-40d2-9981-fe668bca5811%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.



--
Marcus Ottosson
konstr...@gmail.com

Enrico Losavio

unread,
Nov 18, 2015, 11:06:13 AM11/18/15
to Python Programming for Autodesk Maya
Hi Marcus,

thanks for the reply. It's a very interesting approach!
I've tried it quickly but unfortunately it seems to not work for some reason.
Here's my code...

import maya.OpenMaya as OM

# read the selection and get the MObject
sel_list = OM.MSelectionList()
OM.MGlobal.getActiveSelectionList(sel_list)
mesh_obj = OM.MObject()
target_obj = OM.MObject()
sel_list.getDependNode(0, mesh_obj)

# get the inMesh plug
dg_fn = OM.MFnDependencyNode(mesh_obj)
plug = dg_fn.findPlug('inMesh')
print plug.isNull()
# get the MObject from the plug
inMesh_obj = plug.asMObject()
# initialize the MFnMesh
fn_mesh = OM.MFnMesh(inMesh_obj)
# get the point array
point_array = OM.MPointArray()
fn_mesh.getPoints(point_array)
print source_point_array.length()

it works ok until the plug.asMObject() command.
I get

# Error: line 1: (kFailure): Unexpected Internal Failure
# Traceback (most recent call last):
#   File "<maya console>", line 15, in <module>
#   File "c:\builds\maya-2014-w64\build\Release\runTime\Python\Lib\site-packages\maya\OpenMaya.py", line 9233, in asMObject
# RuntimeError: (kFailure): Unexpected Internal Failure # 

But if I create a cube, select the shape and run the script, then it works fine.

I don't know where the problem comes from. Maybe it's a Maya bug, or maybe is just something you can't do with referenced nodes.
If I try to import the object from reference and run the script again, I still have the same error. I suspect that Maya handles reference node as special nodes, thus it doesn't really fills in the correct data into the inMesh attribute.
In my code I also put a call to print plug.isNull() which returns always False (meaning that the plug is not empty), but still the plug.asMObject() raise an Unexpected Internal Failure


I also tried to list the attributes into the 'reference' node (the hidden node, with the blue diamond icon) but I couldn't find anything interesting.

What do you think?

Enrico Losavio

unread,
Nov 18, 2015, 12:40:50 PM11/18/15
to Python Programming for Autodesk Maya
Quick update.

Basically the code above is fine except for one thing. The attribute I have to read is not "inMesh", but rather "cachedInMesh"
From Maya's Mesh Node documentation...

which is possibly what I am looking for.

If I try to apply this point information to another compatible mesh, I see that it goes back to the mesh original state.
Anyway, it doesn't work in all cases.

Say that I have my mesh referenced in Maya, I select it, I send it to Mudbox, and then after some tweaking I send it back to Maya.
At this point if I run the same script (querying the cachedInMesh attribute), i get the same error as above (Unexpected internal error).
This means that for some reason now that attribute is not valid anymore. Or it was somehow modified by Mudbox...

If I open the Hypergraph I see that there's a new shape node (that is the mesh from Mudbox) whose outMesh goes straight into my referenced mesh's inMesh. Whether I disconnect it or not, the script will fail anyway.

I thought I got closer to the solution, but I can't really call it done yet.

Any suggestion anyone?

Thanks



Enrico Losavio

unread,
Nov 23, 2015, 6:06:48 AM11/23/15
to Python Programming for Autodesk Maya
Hi,

after further testing, I'd say that the inMesh, or cachedInMesh, attribute is not the way to go.
Maya does save the initial state of the mesh (as explainede HERE) in these attributes, but it's quite hard to tell when it is gonna happen.
I need to access information about the mesh as it was at the time of being referenced, and I need to be 100% sure that the data I'm retrieving will be correct.
I've seen that in some cases, both the inMesh and cachedInMesh attributes of my referenced shape node are invalid, which means that I cannot rely on them.

As Marcus Ottosson says, I could try to reference the mesh again, read that, and then unload it, but I think there have to be a better solution.

Does anyone know any other way to access this data?

Cesar Saez

unread,
Nov 23, 2015, 7:03:04 AM11/23/15
to python_in...@googlegroups.com

Maybe this is a stupid suggestion, but have you considered to save/update the data when you assemble/update the shot? (as reference in your metadata, side file or whatever fits best your pipeline).

Enrico Losavio

unread,
Nov 23, 2015, 7:29:00 AM11/23/15
to Python Programming for Autodesk Maya
Actually that was the original idea. I was saving out the mesh information i need in a separate file, but it was not enough for our pipeline. The referenced mesh was changing continuously, so that's why I tried to go this way.
The purpose of referencing in this case, is to create a 'live' connection with that object, so that whatever stage the referenced mesh is at, the artists can easily have the most updated version, and at the same time I can know exactly which file they are working on.
I can still save out this data for each single file which is published and used the reference name to read the relative file, but although it works I think it is a bit messy, and I'd like to find a cleaner solution.

So thanks for the suggestion, but the hunt is still on! :)

Marcus Ottosson

unread,
Nov 23, 2015, 7:58:28 AM11/23/15
to python_in...@googlegroups.com
Enrico,

If you plug anything into the inMesh slot, the data there previously will get wiped out.

During load, Maya will fill this slot with the mesh from the file, given that references are loaded first (see any .ma file for reference on ordering), but then continue on to replace this data with that from its incoming connection.

This data then persists, even if you disconnect from inMesh afterwards. (But probably re-appears if you reload the scene at that point, given that no incoming connection will wipe it out once loaded, though I haven't tested and wouldn't rely on it).

If you can find a way to *not* plug anything into the inMesh, then your referenced mesh will remain untainted in this slot. One way of doing that might be to blendshape the original mesh with the mesh coming in from Mudbox.

--
You received this message because you are subscribed to the Google Groups "Python Programming for Autodesk Maya" group.
To unsubscribe from this group and stop receiving emails from it, send an email to python_inside_m...@googlegroups.com.

For more options, visit https://groups.google.com/d/optout.



--
Marcus Ottosson
konstr...@gmail.com

Reply all
Reply to author
Forward
0 new messages