Arnold 5 and Xgen – Bring back the uparamcoord and vparamcoord
Before Arnold 5 (aka: in the alShaders time) it was possible to map a texture to xgen with UV coords using the underlying geometry -patch- UVs
This is not longer possible, unless you do a bit of a workaround, but you can!
The Trick (Long history short)
We need to bake a uv coordinates map into a ptex, using the geometry (patch). Once we have the ptex, we can add its R and G channels, as custom shading attributes in xgen.
Then we can read the uv coords in arnold with an aiUserDataFloat to retrieve the UV Coords. And you can map the xgen without hassle
The Details
The uv coord map
A simple linear (raw) 16 bits uv map will do the trick. As we will bake the ptex using maya, and not the console, we need to use a 16bits float image.
Here is the nuke script that would generate the required image, just copy this text and paste in nuke.
Notice that the image format is TIFF, and the extension is iff. This is a conscious setup, as mayas ptex bake takes iff files, and iff files are essentially tiffs.
set cut_paste_input [stack 0] version 11.1 v3 push $cut_paste_input Ramp { output {rgba.red -rgba.green -rgba.blue rgba.alpha} p0 {100 0} p1 {100 4096} name Ramp1 selected true xpos -148 ypos -178 } Ramp { output {-rgba.red rgba.green -rgba.blue rgba.alpha} p0 {0 100} p1 {4096 100} name Ramp2 selected true xpos -148 ypos -135 } Write { file /path/to/saving/the/uvCoords.iff colorspace linear checkHashOnRead false version 4 name Write1 selected true xpos -148 ypos -97 } Viewer { frame 1 frame_range 1-100 viewerProcess None name Viewer1 selected true xpos -40 ypos -10 }
The issue
xgen u v coords:
A simple expression on the primitive color will highlight the underlying “issue”
Xgen’s u and v coords are based on ptex (aka: per face coordinates)
The expected result
xgen using the patch (geo) u v coords
What we want is the xgen procedural to use the underlying geometry uv coords, shown here
The Ptex baking
Now that we have uvCoords map (the iff generated from nuke), we can proceed to bake it into the geometry ptex map.
Create an image node in maya called uvCoords
Point the image node to the uvcoords map created from nuke
Set the colorspace to raw (or linear, raw, AcesCG etc)
Run the command below replacing your geometry name, and the path where to create the ptex
Notice: a tpu (texels per unit) of 100 is low resolution enough, but depends on the size of your geometry and the faces.
Start with 100, if you notice file size of your new ptex is under 15Mb… you know is low res… try to raise it, and test it on render before you marry to a tpu for your geometry
ptexBake -inMesh myGeo -outPtex "/path/to/where/to/save/the/ptex" -bakeTexture uvCoords -tpu 100
Now, drop that ptex file into this folder:
{YOUR_XGEN_FOLDER}/{YOUR_XGEN_COLLECTION}/{YOUR_XGEN_DESCRIPTION}/paintmaps/uvTexture/
don’t rename the ptex file name, its a requirement that the name of the file matchs the name of the geometry
Viewport Testing
In the Primitive Color attribute, add this line to load the new ptex map
map('${DESC}/paintmaps/uvTexture')
Boila!
Custom Shader Parameter
Now we need to tell xgen to expose this map, in a way we can use it in arnold.
Good old times sake, lets call this parameters uparamcoord, and vparamcoord 🙂
notice: the expressions will need to refer to the R, and G channels for u and v
map('${DESC}/paintmaps/uvTexture')[0]
map('${DESC}/paintmaps/uvTexture')[1]
Read the values from arnold
Create aiImage node and load any texture (i got a leopard skin texture from google)
create 2 aiUserDataFloat
name one uparamcoord and set its Attribute to uparamcoord
name one vparamcoord and set its Attribute to vparamcoord
connect the output of uparamcoord to the aiImage.UvCoords.X
connect the output of vparamcoord to the aiImage.UvCoords.Y
Now you can use your image in your xgen, and the xgen will be mapped according to the geometry uvs!
NOTES:
The uparamcoord and vparamcoord will not work on any shading node that has explicit uvs (for ie: most procedural nodes will not work)
Everytime there is a change in the UVs, the uvCoords ptex will need to be rebaked
UV value precision: this can be a long point of discussion for sure. You can bake the ptex from a 32 bits uvCoord map using the ptex command line tools (not from maya) if you care that much about precision
Udims: still to test if ptexbake supports udims, ill expand on this later