Enveloping rigid elements

August 21st, 2006 by Helge Mathee - Viewed 24583 times -




Alright, here’s a new article of mine. This time I am dealing with a problem a lot of people are facing when trying to envelope a large number of objects onto a surface, while the objects themselves are not supposed to deform. As this is a typical problem related to objects like feathers, all scripts + tools are named somewhat related to feathers. All of these techniques can be applied to other objects as well, though.

Lets start. One easy way to approach this problem is to create a mesh including all objects we want to envelope, and then simply set the envelope weights of all points of a single instance to the exact same weight, aka:

In this image we have a mesh with 6 cubes (all merged together) enveloped to a two-bone chain.
By default the weight is blended in the middle part,

which results in a deform for the middle two cubes:

by using the weight editor, I adjusted the weight of all cubes so they only target one bone:

which results in movement, but not deformation for each one:

So this is all working, why bother dealing with a system to deal with these things? Well, as long as we are dealing with six cubes it is all cheesy and simple, but as soon as we start dealing with something like feathers on a bird, we can’t just go in and envelope each feather with the weight editor, well, we could, but it would just take forever.

What I used to do in those cases is to build an instancer operator, which would take a mesh containing “where-and-how-to-instance” information, and a single mesh which is supposed to be instanced. First, lets clarify the “where…to-instance” part:

When instancing an object, all you need is a position, orientation and scaling, which can be stored as three points really, but in this example I am going to use 4 points:

1. Pos: The position of the object to be instanced
2. Cns: The Z-Direction of the object (seen from pos)
3. Upv: The Y-Direction of the object (seen from pos)
4. Bnd: An additional point to be used for deformation (later)

So basically we could draw a quadrangular polygon instead of four points, like below, where we are instancing ten grids:

Now: Instead of enveloping the objects we want to be instanced, we envelope the mesh containing the quads. This is going to be called our “Instancing-Cloud”. It contains all of the information we need to instance our objects. Moreover, it is easy to envelope, as we know exactly which points are to be enveloped where. Every first out of four points is the position, every second out of four points is the z-direction etc… All we need to build is a couple of scripts:

1. One which adds a quadrangle to a mesh based on a transform of a null.
2. One which creates a new mesh and instances an object onto an Instancing-Cloud.
3. One which generates clusters for the instance-cloud for easier enveloping.

A finished setup could look something like this: We see the quads representing the instances:

When deformed: The quads deform, but the instances will not:

Including the instances it should look like this:

When deformed:

As we have point clusters for each type of point in the instance-cloud (pos, cns, upv and bnd) it is quite simple to rig the cns for example to a bunch of rotational controllers:

And when we rotate them, only the cns points are deformed, therefore the instances rotate as well:

Additionally we can deform the cloud overall:

So now lets discuss the last part of the story: What’s the bnd position for?
The bnd position is used for deformation of each instance. As this is quite limited, all I am going to do is move the instances points using a sinus function, to get somewhat of twisting and bending going on. This is up to your imagination, as I said, this setup has been used for feathers, that’s why the bnd position is used for bending (and named like that as well: bnd = bending).

In the next image I rigged the bnd position to the rotational controller earlier used for cns, to show what happens:

So now when I rotate them:

Or along another axis:

As always – I’d like to share the progress so far, but I have to warn you, it is not at all documented:

Put the file into one of the plugins folders, and run the following script to get some feather setup going:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
NewScene(false, false);
var cloud = mt_createFeatherCloud();
 
var grid = CreatePrim("Grid", "MeshSurface", null, null);
SetValue(grid+".grid.ulength", 0.4);
SetValue(grid+".grid.vlength", 3);
SetValue(grid+".polymsh.geom.subdivu", 1);
Translate(grid+".pnt[*]", 1.4, 0, 0, siRelative, siLocal, siObj);
FreezeObj(grid);
 
var mesh = mt_createFeatherMesh(cloud, grid);
var feathers = new ActiveXObject("XSI.Collection");
for(var i=0; i<10; i++)
{
feathers.Add(mt_createFeatherNull());
feathers(i).kinematics.local.posx.value = i;
}
 
mt_addFeathersToCloud(cloud,feathers);
mt_createCloudClusters(cloud);
 
DeselectAll();

Let me know how it goes,

enjoy!

11 Responses to “Enveloping rigid elements”

  1. Fantastic Helge!
    Im currently on a project that need feathers, and this come in good time!
    i tested your scene ajusting loop creation for 1000 feathers, and on my machine deforms slow down very much… (dual core 3.8Gz/2Gb ram)
    i tested again with loop for 100 feathes, and it be very useable speed.

    the question is…. how can put this feathers on surface of a Subdivision Surface wing?
    and, you have plans for colision between neighbourhood feathers, like on Margalo and falcon system of Stuart Little II… ?
    So.. congratulations for now..
    and, i want to help you to test this system.

    PS: Actualy im starting to program in python for XSI.
    Stay in touch.
    Thanks for your tallent! ;)

  2. Helge Mathee says:

    well – in the test script I submitted all feathers remain live and connected to the nulls which created them. if you freeze the cloud object you should get an enormous speed increase.

    you need a distribution algorithm on how you want to put the objects onto a surface, all you need to create is the cloud, envelope it (maybe using gator) and the instances will move correctly with the wing. this algorithm does not deal with interpenetration – it is only dealing with the instancing part.

  3. Matt Lind says:

    This setup reminds me of a rig somebody did back in the old Softimage|3D days with a parrot (circa ~1996). Instead of using enveloped quads, they used 2d chains as the 2-points to guide the instanced feathers as it allowed the effectors to be driven by curves, constraints, or Fcurves to make the feathers rotate. I cannot remember for sure, but I think the feathers were then deformed by Qstretch or curve deformation on top of the transforms supplied by the 2D chains so the feathers could bend with a little time lag in relation to their motion. gave a semi-realistic quality that was artist friendly to control.

  4. Malcolm Zaloon says:

    Ok, i understood .. only instancing…

    I tried freeze featherCloud, and have some speed improvement (around 35%). Very cool!

    so, how can i control scale of feather? I see that nulls only controls the ori/pos of feather.

    thanks again Helge.

    I have other technical Question… i remmember that your scripts are VB… but now, i see this in Js… Are you migrated? If yeah, why? Its faster?

    thanks again Helge.

  5. That”s a really interesting approach.

    I had a play around with it earlier and was surprised to see that if you create a “cluster with center” on the Bnd points, you don”t get any deformation when you animate the bones (providing the ClusterCenter operator is underneath the envelope operator). You”re then able to animate the cluster null and get correct deformation regardless of bone position. V handy for rigging setups.

  6. Hidekazu Shimana says:

    Hello Helge-san

    I would like to introduce the this page for Japanese XSI user. So, I will transrate the this web page.
    Would you like to introduce the transleted page on My company”s web site?

  7. Helge Mathee says:

    Sure. Email me privately my email is in the profile page.

  8. luz says:

    Interesting ! Listen do you have idea how to create rolls divison for a bone chain of
    4 bones ? and lets says I need 4 rolls division for each bone.
    If you know how to to do that, can you describe it step by step ?

  9. [...] 93@N00/243434839/” title=”photo sharing”> useful ideas for rigging feathers a wing: link This entry was posted on Thursday, September 14th, 2006 at 10:3 [...]

  10. David says:

    to Luz, yes, there’s a way to do that, but you have to trick XSI, if you look the SDK help, you will find a few commands that are quite helpful, the MakeBicepRoll, and MakeForearmRoll (or something like that, I don’t have XSI open right now, just do a search for biceproll or forearmroll in the help and they will pop up) very handy :)
    if you have any questions you can email me
    djaguilar3d@yahoo.com