Instance/copy objects with nulls

Hey there,

when dealing with real commercial productions it is, at some point, necessary to place object instances by hand. There for you have four options in Softimage.

  1. A hard copy of the object
  2. A clone of the object
  3. Put it in a Model and use an model instance
  4. Use ICE to distribute instances in combination with Nulls that have an PPG with an integer attribute to detect the instance.

Point four is the workflow I like the most, because it is super flexible. After the placement it is possible to change all attributes e.g. with a random size or position. Now the question is, how do I adapt my known workflow to Houdini? Exact the same way I do it in SI. Fist we need to create a null object with an integer attribute “instNR” for instance number, some instances and a geometry that holds the geometry.

Lets dive into geometry level. First I have tried to build a setup the classical way. With maaaany attribute create sops. 

“Going from top to bottom you see that I create all attributes I need to transfer the data from the null objects: i@instNR, f@pscale, v@scale, v@euler_rot, 4f@orient. In the point vop I convert the euler rotation to a quaternion rotation. This is needed because the copy sop is using quaternions. With the path attribute of the object_merge sop we can access all attributes like this: ch(@objname + “/../instNR”). The only attribute we have to samp is the Instance Number. The syntax in the copy sop is like this: point(“../Input_GEO_OUT1”, $PT, “pinstNR”, 0). The switch node can now access this attribute like this: stamp(“../copy_InstancesToPoints”, “pinstNR”, 0). This is all we need to get it working.

Much slicker is to do all attribute manipulation in an attribute wrangle.

That’s all. Easy to setup and effective. The only thing to notice here is, that this is a copy NOT a instance workflow. To really instance objects I recommend this tutorial. https://vimeo.com/55292609 this workflows here can easily combined with this workflow. Here InstanceObjectsWithNulls you can download the example hip file.

Point in Volume (Feat VEX)

Hey!

In my last post I showed a simple “Point in Volume” VOP. Inspired from the Side FX VEX Webinar I ported this logic to VEX with an attribute wrangle.

float maxdist = ch("maxdist");
int maxpts = ch("maxpts");
@Cd = {0,0,0};

int closept[] = pcfind_radius(1, "P", "pscale", 1.0, @P, maxdist, maxpts);
i[]@closepoints = closept;

foreach( int pt; closept){
        vector pc_pos =  point(1, "P", pt);
        vector pc_normal = point(1, "N", pt);
        vector oCompo1 = pc_pos - @P;
        f@weight = dot(pc_normal, oCompo1);
}
if(@weight > 0){
    @Cd = 1;
}

Quite easy AND quite cool. Let’s explore VEX a little more  😉

Soft Contact Deformer

Hey!

In commercial work every artist had the case to place/ distribute/ scatter water droplets on to other objects. During the last days an artist came to me who had placed may spheres by hand and was annoyed of the shaping process after the placement.

So I made an easy usable setup in houdini, that enables the artist to do some basic contact shaping.

Here is my graph. First we need a Droplet Sphere and a Target object. The first needed step is a “Point in Volume” Point VOP. I do it in this way because a Group SOP is much much sower. So let’s dive in and this is what we’ll get.

As you see above, with the pcopen I do a closest location query and extract the closest P and N variable. Cool, with some math we get just 0 and 1 values. We’ll use this information later in the tree. With this done we can use an attribute promote to calculate the sum of point that are inside the target volume.

Then we use an attribute create to get the point percentage that is inside the volume. (This retuns values between 0-1)

In this VOP happens all the geometry manipulation. Stating at the right, we find a two way switch where we use the PointInVolume attribute to do either a shrink wrap or to do a simple push along the normals. As you go through the graph you will notice the detail import detail (percInVolume) that is a multiply for the push. With this method we make sure, that the normal push after a single point is in the target volume. I’m sure that it is possible to combine the two point vops, but I’ve still not found a way to do the attribute promotion on vop level. The rest is just an smoothing and subdiv sop. Nothing fancy.

Andreas

 

“Easy Voronoi Mesh”

Yesterday I saw this.

My first thought was: You can’t be serous. Such an easy thing is is soooo difficult and nondestructive. In Houdini this is much easier and changeable. Here is my graph.

All you need is a Scatter and Voronoi SOP to cut the geometry. Than, loop over all pieces, insert the faces, connect the boundary edges with the fuse sop, add some depth to the geometry, subdivide it and finally give it the right normals with the facet SOP. That’s all you need to do.

Retiming Houdini caches with changing point counts

Hey all there,

when it comes to do fluid simulations in Houdini it is often necessary to be able to re-time the caches after the simulation. In principle that is not a big deal – just an interpolation between two frames. It gets a little harder if we have a constant emission which leads to a changing point count. In this case we have to build a setup like this.

First we start with a Null that gets three float Parameters as a input (Current Frame, Frame A and Frame B). The Current Frame should have an Animation on it, and the two others get a nice little Python snippet:

Frame A

import math
FrameA = ch(“CurrentFrame”)
return math.floor(FrameA)

Frame B

import math
FrameB = ch(“CurrentFrame”)
return math.ceil(FrameB)

Next lay down two File nodes and input the simulation.

$HIP/geo/SimulationTest.filecache1.`ch(“../Time/FrameA”)`.bgeo

$HIP/geo/SimulationTest.filecache1.`ch(“../Time/FrameB”)`.bgeo

With this done we’ll always get the Current Frame and the next frame as inputs. An example would be: Current Frame 55.8 => Would be Frame A = 55 and Frame B = 56. Since the Frame A always has the lower point count we need to make an detail attribute “nptA”, that holds the point count of Frame A. With the help of an attribute transfer we can copy the detail attribute to the Frame B stream. In the delete sop that follows the attrib transfer we throw away all the new points of Frame B, so that we can interpolate the Points of Frame A with Frame B. There for use this little expression $PT >= @nptA.

The logic happens now in the pointvop. Connect the two streams and create two parameters: A velocity mulitply and a attribute blend float. On sop level the attribute blend parameter gets this expression: ch(“../Time/CurrentFrame”) – ch(“../Time/FrameA”) the result is always a blend value between 0-1, that we can use for mixing values in the point vop. The velocity muliply parameter gets this expression: chf(“../Time/CurrentFrame”, $F + 1) – ch(“../Time/CurrentFrame”) the result is a the difference between the Current Frame  (of the Time Null) and the next Value on the fcurve of this parameter. I do that to make sure that the velocity scales proportional to the retiming curve. The nodes of the pointvop are just some mixing and binding. Note: If you have other attributes that you want to interpolate just also import them for the two streams and blend them. Yeah!

When this is done we have to care about the other new points that will be born on Frame B. Because I have no information when the Particles where born between the two frames I add them randomly over the animation time with the now expression. @randomDEL > ch(“../Time/CurrentFrame”) – ch(“../Time/FrameA”) Check my post if you want to now more about how you do a “Test Random Propability in Houdini)

The rest is just merging and cleanup. A last quick node. If you use the fluid compress node in combination with a compressed bgeo file it can happen, that the point index changes from frame to frame. This leads to an improper blending.

I hope you like my solution. If you have questions or acknowledgements, please drop me a line.