get 和set语句原理很简单,但非常好用,因为可以直接联系到RealFlow的用户界面。这两个命令完全共享同样的名称,你可以在节点(Nodes)和节点参数(Node Param)窗口看到。主要区别是get和set命令需要的参数(number)和数据类型参数不同。这命令不仅可用于遍历粒子,它们可以用在任何地方。



  在这个例子里,Cone(圆锥体)已经添加到场景。参数列表包含了所有你需要使用的对像参数。最有趣的参数都在Node 标签下。在这你能找到最基本属性,像位移(position),Rotation(旋转)或Scale(缩放).在线帮助文档介绍的相应的get参数如下:

  any getParameter( any )

  告诉我们getParameter命令可以使用任何对像或任何数据类型。操作不限于参数,发射器,或摄像机。数据类型也可以是Integer,Float,Vector等。

  你的数据类型可以使用getParameter命令,从Node标签下读出。当你看到三元值时,一定就是矢量:

  Position 0.0 0.0 0.0

  Rotation 0.0 0.0 0.0

  Scale 1.0 1.0 1.0

  Pivot 0.0 0.0 0.0

  请注意:单个的矢量值(分量)是Float类型。甚至颜色也是用三个值,红,绿,蓝(RGB).Simulation和Dynamice数据类型是String(字符型).字段可以包含字句或表达式:

  Simulation Active

  Dynamics No

  如果WetDry贴图设置为Yes,你可Integer值,像

  @ resolution 256

  @filter强度和@ageing值也是Float类型。

  如前面所说,你要知道,get命令会输出什么数据类型,因为是setParameter的逆过程。你用确切的数据类型去改变合适的值。让我们看一个例子:

  cone = scene.getObject("Cone01")

  pos_global = cone.getParameter("Position")

  结果是一个矢量,由三个Float组成。当计算完成后,你可以建立一个新的矢量。新的向量必须也要有三个Float(integers也是可以的)。你不能用String去替换。不然会产生语法错误:

  pos_new = Vector.new("left", "up", "right")

  下一个例子是一个完整的脚本。在RealFlow里准备一下,脚本作用是给圆锥y轴每帧位移增加0.2:

Events Script: ChangeConeYPos.rfs

  def onSimulationFrame(): cone = scene.getObject("Cone01") # 1. Get global position data in Vector format pos_g = cone.getParameter("Position") # 2. Get components from the position Vector pos_x = pos_g.getX() pos_y = pos_g.getY() pos_z = pos_g.getZ() # 3. Add 0.2 to the y component new_pos_y = pos_y + 0.2 # 4. Build a new Vector new_pos_g = Vector.new(pos_x, new_pos_y, pos_z) # 5. Use the new Vector for position change cone.setParameter("Position", new_pos_g)

  这个脚本与第三节的事件脚本非常相似。那个脚本增加了y和z方向 所有粒子位移。这里,我们只是针对单个对像。get语句过程的,分离和组合是和向量一样的。主要不同是最后一个语句:

  cone.setParameter("Position", new_pos_g)

  对于粒子,是这样:

  particle.setPosition(new_pos_g)

  注意粒子与别的对像是使用不一样的set和get命令。对emitter或mesh,是可以直接在对应Node参数窗口看到值的。Position或Velocity值不是都显示出来的。他们在内部使用。为了更快的访问速度和更好的区别,粒子属性不使用Parameter关键字。

  还有另外一个不同点:getParameter命令只能取得一个参数,名称是“position".setParameter显示了”position"和new_pos_g.

  因此用setParameter你必须要告诉RealFlow你想用哪种类型的数据改变(Position,pivot,roughness),然后新的值要用正确的数据类型。

  在模拟时,可以在节点参数窗口监视更改的值。只是试一试y分量的position值。


圆锥在Y方向有一个恒定运动。


小提示: 不要从直接从本文章复制脚本到RealFlow。不一样的字体,字符设置和空格,都将导致错误。手动输入脚本是最好的,还能思考脚本到底是如何工作的。


  用getParameter和setParameter能获得很多乐趣,因为你能更改,改变,打开关闭几乎所有东西。一些任务可以手动方便的解决,但脚本更精确一点。特别是碰撞,有时不能轻松的得到完全相同的碰撞。在两个模型,或粒子之间。使用Python脚本,解决起来只要短短几行代码。这是初始情况:



  我们目的是让物体落下,碰撞到地板。所有物体都处于不同的位置。手动停止他们,可能很难。这个场景仅有三个模型,但假如有 20,30,或60个模型呢。根据你现在为止看到的方法,我们一直调用单个对像,如果有更多的对像时,就变成一个麻烦的事。为了使这个任务轻松,Realflow 有强大的对像选择工具。操作是,我将要用这个命令,名称是:

  getSelectedNodes()

  使用这个命令,你可以在节点窗口里选择到你想起作用的对像。

  RealFlow分辨出你选中的,再把所有对像存储到List对像中。正确的表达式是:

  items = scene.getSelectedNodes()

  相像一下:选中三个对像,圆锥体(Cone),方盒(Cube),圆柱体(Cylinder),内部元素就会是:

  items = [Cone,Cube,Cylinder]

  下一步就是搜集所有正在碰撞到地面的对像项目。RealFlow也有能达到这个目的的函数。用这个命令要再创建一个List数据类型,因为有不只一个对像碰撞到地面:

  floor = scene.getObject("Floor")

  colliding_objects = floor.getCollidingObjects()

  现在,我们要通过列表浏览碰撞对像并适当停用掉原始物体

  if (colliding_objects != [ ]):

  for object in colliding_objects:

  object.setParameter("Simulation","Inactive")

  用if条件语句检查,List colliding_objects 是否空的。表达式是

  if (colliding_objects != [ ]):

  意思是:如果 列表 colliding_objects 不等于空的,不执行下下面。空的列表写作[ ].你一种方法是检查列表长度(len)。

  如果碰撞物体检测到就把存储到colliding_objects.并把Simulation参数设置为Inactive(不活动)。换句话说:当物体一完全碰撞到地面,就会被设置为不活动,并释放封闭的流体。下一页你将看到这个脚本的列表。


Events Script: InactiveOnCollision.rfsdef onSimulationBegin(): items = scene.getSelectedNodes() for object in items: object.setParameter("Simulation", "Active") object.setParameter("Dynamics", "Rigid body") def onSimulationStep(): items = scene.getSelectedNodes() floor = scene.getObject("Floor") colliding_objects = floor.getCollidingObjects() if ( colliding_objects != [] ): for object in colliding_objects: state = object.getParameter("Simulation") if (state == "Inactive"): pass else: object.setParameter("Simulation", "Inactive") object.setParameter("Dynamics", "No")

  第一步分是初使化选中的项目并设置为活动。这在初使有多个模拟传递的情况下很有用,因为你不用每次模拟这个场景都要切换到之前值(初使值)。

  程序能识别所有与地面进行碰撞的物体,并把它们存储到List变量中:

  colliding_objects = floor.getCollidingObjects()

  最后的if语句只是做很小的(建设)检查,Simulation状态是否改变了。所以如果Simulation状态设置成Inactive,脚本什么也不做。




  碰撞后溶解(散开)

  唯一的不足是,物体要与地面进行完全碰撞(后才能散开),之前他们都是失活(inactivate)状态。

  第一次接触后就保持活动状态。一个繁琐的方法是利用模型的面或点进行检查。你可以把碰撞的面加入到一个列表。如果列表的长度大于0,物体就变为活动。

  然后检查每个步骤或帧的对像状态是否活动,优化脚本。


,realflow教程,realflow技巧