IsoOffset节点
可以基于原几何体生成offset关系的数据,数值>0 向外扩散,最多可扩散至物体boundingbox,<0向内扩散,fog选项配合scatter可以将点数据深入到表面以内,获得更好的破碎效果。
此时fog的浓度是均匀的,意味着破碎效果也比较单调。既然fog是volume的一种形式,那么就可以用volume vop来修改density属性。通过创造不同的浓度,达到不同大小碎块的破碎效果。
需要注意noise产生随机值,而density值必须>=0,用max函数设定最低值,从而达到过滤掉负值的目的。
可以在noise后加入ramp parameter,需要将数据类型改为float,ramp会自动promote到vop节点界面,通过调节曲线获得理想状态。
Voronoifracture的算法
假设基于scatter只有两个点的平面来做fracture,得到如下图
assemble节点
类似pack节点的算法,勾选Create Packed Geometry将mesh数据转为代理,并不占用当前内存,将用于voronoifracture解算的点作为数据,即,当前点数即为当前数据量,大大节省数据负荷。
注:同时可以在此基础上对点的位置进行修改,以达到理想的视觉效果。
此时rigidbodysolver 需要接受rbd packed object 的输入才能正确解算。
针对rigidbody solver,可以输入pop force 或者在popwrangle用表达式输入,例如
@P.x = @P.x + 0.1;
即为当前输入点在x方向持续添加0.2的位移,结果和在pop force 中添加x方向速度基本一致。
关于voronoiFracture中取消掉的cluster选项,可以参照如下链接
https://www.sidefx.com/forum/topic/59435/?page=1#post-292099
cluster可以将距离在一定范围内的点所对应的碎块绑定在一起,节省了资源,但是由于cluster会导致Convex Hull解算出现错误,所以如果是精细镜头请谨慎使用。大场景可配合smoke和motion blur一起使用,节省解算资源。
Houdini18 在voronoiFracture中取消了visualizer,但是考虑到碎块是由point生成的,可以加入color节点来为point增加Cd属性,值为random,然后通过voronoiFracture中的Copy Cell Point Attributes 中的To Piece Primitives来获得传入点的Cd值,从而达到visualizer相同的效果。
更新: 也可以加入visualizer节点,用需要的属性绑定visualizer的节点也可以实现,比如当前是用点的ptnum绑定颜色Cd。这应该是visualizer节点设计的初衷吧。
此时碎块之间实际是没有相互连接的。尝试在rbd packed object中更改角速度属性,可以发现在碰撞之前碎块已经散开,合理的碰撞应该是从着陆点散开的,而不是同一时间,所以需要添加粘性约束来控制形态。
ConnectAdjencentPieces节点
顾名思义就是将碎块粘合,通过调节以下参数获得理想的黏连关系。
需要注意,ConnectAdjencentPieces的算法是依据碎片绑定的point,所以可能会出现实际物体和point不相连,从而造成破碎关系错误的情况,需要将mesh template仔细查看。
PrimitiveWrangle节点
针对primitive属性调节的VEX表达式节点
s@constraint_name = "CoolGlue";
f@strength = 0.05;
定义约束名称为“CoolGlue”,强度0.05。
注:由此也可以看出,可以通过并行的几个connectAdjencentPieces节点和primitiveWrangle节点来同时控制物体。
ConstraintNetwork在dopnetwork中
将破碎物体和约束分别接入DOPnetwork的第一个点和第二个点,接下来就可以通过语句调用,0为第一个点。这样和通过Null来调用结果是一致的。
`opinputpath("../", 0)`
将constraintnetwork节点置于gravity节点之前,SOP Path指向约束输入点,如果连接成功,Guide Option会显示蓝色。
注:
1.此处的Strength值和之前定义的strength乘积为最终值。
2.DataName必须是已经定义过的字符串,否则会导致constraintNetwork节点报错。
同样的,如果在之前的connectAdjencentPieces和primitiveWrangle中多次定义约束,此处也可以merge多个glueConrel来调用。
在primtiveWrangle中添加一些条件,获得更真实的碎片效果。
s@constraint_name = "CoolGlue";
f@strength = 0.01;
if(rand(@primnum) < 0.15){
f@strength = 10;
}
如果当前随机数返回值小于0.15 则约束强度为原来的1000倍。
拓展阅读:
此处rand()为随机数,houdini中的随机返回值是固定的,(不然演算每次都不一样计算机要累死了),如果想要更改随机返回值,需要更改seed。rand(@primnum)就是以每一个primitive的编号为seed来返回随机数。默认rand返回值的范围是[0, 1]内的浮点数。
打开Guide Geometry,发现Convex Hull并没有像直接使用Cluster一样产生重合,是因为约束将多个碎片的convexHull粘在一起,并没有独立解算。
拓展阅读:
detail表达式
detail(surface_node, attrib_name, attrib_index)
这个表达式可以用于读取 geometry spreadsheet 中detail(第四个)tab下的数值
for each loop模块
for each loop 在Houdini15后取消了,但是通过geometry speadsheet可以发现voronoiFracture输出的碎片“piece”对应的index统称name,所以loop循环需要的是参数"name",在H18中对应的模块则为“for each Named Primitive”,检查loop end 的piece attribute应该也是“name”。
通过表达式detail()从metadate中调用参数iteration
detail("../foreach_begin1_metadata1/", "iteration", 0)
其中detail()语法如下:
detail(surface_node, attrib_name, attrib_index)
因为iteration是一个浮点数,所以序列index为0,符合list数据特性。
在loop中通过switch来添加丰富性
由于switch 只接受 >= 0的整数输入,比较类判断条件的返回值True = 1 False = 0,非常适合作为输入。
rand(12345 + detail("../foreach_begin1_metadata1/", "iteration", 0)) < 0.25
此处利用iteration的值作为seed输入给rand(),
rand()默认返回值在0-1之间。添加常量12345可以使随机值更丰富。
注:如果添加额外条件,则一定要注意是否存在空值情况。如
rand(12345 + detail("../foreach_begin1_metadata1/", "iteration", 0)) < 0.25 && npoints("../scatter2/" > 0)
此时条件为“随机值<0.25 && scatter节点产生了point”,可能会存在缺面的情况,需要适时调整switch条件语句。
将loop输出接入assemble节点,取代原本的voronoiFracture,获得更为细分的破碎效果,可以通过exploded view查看。
另一方面,点数的增加又为connectadjencentpieces节点带来了新的数据,从而有产生计算错误的可能,如下。
另:此时预览动画,发现有些碎块碰撞不自然,检查rbdpackedobject发现,Convex Hull解算出了问题,可能是由于loop内再次细分导致。
此时如果用copy节点复制多个物体碰撞有两种方式
*1.将约束和dop节点同时置于copy节点后
这样是把copy后的点云共同计算,当单体间距较大时可以保证效果,当单体间距变小时可能会出现互相约束的问题。
另,通过观察geometry spreadsheet,发现copy后的name其实是重复了单位几何体的矩阵(piece155在2*2的矩阵中共出现了四次),所以输出到约束的点只是单个几何体约束的复制,相应的解算也会出现问题。
*2.将copy后的点云重新命名并输出给约束
name相同而空间位置不同的点云会导致约束解算失败,
为了达到最理想的效果,需要把复制后的每一个点单独添加到约束内,进一步明确name的指向。
通过pointWrangle节点,将name以点的index序号来重新命名,这样保证了name唯一性,约束解算也变得合理。
语句为:
s@name = sprintf("piece%d", @ptnum);
最终多物体碰撞效果
总结:
1.随时检查rbdPackedObject 里的Convex Hull;
2.随时检查connectAdjecentPieces里的约束是否合理;
3.随时查看Geometry SpreadSheet,观察当前节点内的数据类型;
4.巧妙运用判断语句与 switch 的输入;
5.voronoiFracture产生的碎片内面是不带UV的,但是会将内面分在inside组下面,可以用UV unwarp 和UV Layout配合重新排布UV,需要注意不要和外部UV重合。