CG橙子精彩导航: CG橙子搜索引擎 | 博客 | 动画视频
广告|项目|培训|竞价排名  
86CG > CG教程 > 虚拟现实 > EON Reality > 在EON撰写程序指导方针

在EON撰写程序指导方针

类型:整理 | 来自:86CG | 时间:2007-11-26 |  点击:

  在Script 节点中所储存的数值就如同VBScript 的语法。而程序撰写节点 (Script node)里的evenIn及exposedField收送区域,可编写为On_name()的子函式。当程序撰写节点收到输入事件(in-event)时,子函式将被执行。

  当以VBScript数据来撰写程序,有利用到多重函数字段(如含有SFVec2f, SFVec3f or SFColor数据型态)时,则独立的数值必须先被分配为数组 (array) 才可被执行。当程序撰写 (Script) 节点的位置收送区域接收到输入事件,如下列范例所示的子函式将会执行运作。它指定SFVec3f输入事件至名为p的VB数组,当数组的数值增加1后,则指定为newPosition的输出事件。

sub On_position() 
p=position
p(0)=p(0)+1
p(1)=p(1)+1
p(2)=p(2)+1
newPosition=p
end sub


  当数组所指定的工作被执行时,含新数值的事件将立即被传送至相关连结的功能节点。

  但JScript只能读取VBArrays (同时也称为Safe-array) ,因此EON支持四种补充功能用来建立Safe-arrays,分别为SFVec2f, SFVec3f, SFColor 和 SFRotation型态。每个函数皆回传一个VBArray。请看下列有关EON函数的章节。

布尔值
  当使用script里的VBScript和Boolean字段时,TRUE值会被转换成为 –1,这是由于Microsoft设计VBScript时之定义。而JScript则转换TRUE值为1。

  为避免任何的混淆,我们建议您不要使用Boolean字段的数值。举例来说,IF叙述应当以如下所示的范例来写。

if MyBooleanVariable Then 
DoSomething
end if


下列的两个范例将显示不使用Boolean的情况。

if MyBooleanVariable = TRUE Then 
DoSomething
end if

if MyBooleanVariable = -1 then
DoSomething
end if

提示:将您的Boolean因子命名成问题型态,如下所示的范例。


if AboveFloor AND BelowRoof then
ShowFurniture
end if

EON功能

有些EON函式库功能可能是由scripts呼叫。

EON.MakeSFVec2f

建立EON用来表现SFVec2f数据型态的Safe-array。

EON.MakeSFVec2f(x, y); 
EON.MakeSFVec3f

建立EON用来表现SFVec3f数据型态的Safe-array。

EON.MakeSFVec3f(x, y, z); 
EON.MakeSFColor

建立EON用来表现SFColor数据型态的Safe-array。


EON.MakeSFColor(r, g, b);
EON.MakeSFRotation

建立EON用来表现SFRotation数据型态的Safe-array。

EON.MakeSFRotation(x, y, z, a);

比较以下的JScript范例与如上所示的VBScript的范例。

function On_position() 
{
ar p = position.Value.toArray();
p[0] = p[0] + 1;
p[1] = p[1] + 1;
p[2] = p[2] + 1;
newPosition.Value = eon.MakeSFVec3f(p[0], p[1], p[2])
}
Trace()

给予SFString, Trace()功能将显示在EON事件记录窗口 (Log window) 所输入的字符串。

EON.Trace("Value ball = " & ball & "!") 

  此行列显示事件记录窗口内的"Value ball = 9 !"的讯息。请确认在事件记录过滤(Log Filter)窗口里Log型态(types)下的Debug是为勾选。

eon.GetNodeName

得到一个功能节点的名称。


name =eon.GetNodeName(aNode)
eonGetNodePath

传回一个含有完整路径的字符串给节点。

eon.GetNodePath(aNode) 
eon.Find()

  寻找节点是吻合名称或此规律。使用此eon.Find()函式来取代只能传回第一个相符合条件的旧Find()函式。

  Rooth和maxdept是为选择性的。名称可完全一样或是一个Regexp对象(只在JScript和VBScript有效用的)。有关Regexp更多的讯息请看Microsoft的手册内的VBScript和JScript单元。同时也请看下面所示的 “Example 2 in VB Script"。

  如果未指定rooth,那搜寻的动作将会从模拟节点(simulation node)开始。此基础功能节点总是包含在被搜寻的动作内。

IMaxdepht=0 搜寻(Find)函数只应用于基础节点。

Maxdepht =1 搜寻(Find)函数应用于基础节点和其子系节点。

如果未指定maxdepth那么内定值是没有限制的。

如果maxdepth是小于0,那收寻结果永远是空白的。

  这些节点将依序显示出。举例来说,首先在基础节点中找到的子系节点会列示出来,第二将显示出其孙系节点,依此类推。

eon.Find(name, root, maxdepth) 
eon.Find(name, root)
eon.Find(name)
eon.Find(regex, root, maxdepth)
eon.Find(regex, root)
eon.Find(regex)
Example 1 in VBScript:
Set nodes = EON.Find("Ambient", aNode)
eon.trace("nodes.Count = "& nodes.Count)
If ( (nodes.Count > 0) ) Then
Set firstNode = nodes.Item(0)
End If
Example 2 in VBScript:
rootnode_path = "simulation!scene!cube1"
Set rootnode = EON.FindNode(rootnode_path)
Set rexp = new Regexp
rexp.pattern = "Rot.*"
maxdepth = 1
Set nodes = EON.Find(rexp, rootnode, maxdepth)
For Each n in nodes
Set nn = n
eon.Trace("Found node " & eon.GetNodeName(n) )
End If
Next
FindNode()

  指定一个SFString,FindNode()函数将会寻找在仿真程序中第一个被找到含有指定名称的节点或是回复为”空值(NULL)”的状态。

set aNode = EON.FindNode("UniqueScript")

  藉由使用关键词的设定,这个叙述建立一个参考变量名称为aNode。任何对象变量的更改将会影响UniqueScript节点。

  以下范例是为一个脚本(script)当它接收到一个名为MoveCamera的输入事件时,将模拟摄影机 (simulation camera) 移动指定的距离。在此范例内此输入事件的数据型态为SFFloat。

此子程序将会沿着X轴移动摄影机x pos像素:

Sub On_MoveCamera 
' Find the Camera node
set CameraNode=EON.FindNode("Camera")
' Get a reference to the camera position
set Pos=CameraNode. GetFieldByName ("Position")
' Get the value
p=Pos.Value
' Increase the x pos
p(0)=p(0)+MoveCamera
' Assign a new value to the camera position
Pos.Value=p
end sub

为寻找Camera节点,EON函数FindNode将派上用场:

set CameraNode=EON.FindNode("Camera")

当一个参考窗口节点被保留,那必可找到位置(position)字段:

set Pos=CameraNode. GetFieldByName ("Position") 

p=Pos.Value

沿着X轴来移动模拟摄影机 (simulation camera) 乃藉由下面所列示的行列来完成:

p(0)=p(0)+MoveCamera 

请记得指定摄影机新的位置之数值:

Pos.Value=p 
SetScriptTimeout()

  如果一个脚本(script)已经执行超过六秒 (内定暂停时间),藉由使用此函数来使讯息盒 (messagebox) 关闭或是延迟它的出现。

  呼叫这个函数来设定一个浮点数型态(float)来表示一个新的暂停时间数值 (此数值是近似值,以秒为单位)。如果不启动messagebox,可将此数值设定为 value=0.0。

oldtimeout = EON.SetScriptTimeout(0) 
msgbox "Hallo!"
EON.SetScriptTimeOut(oldtimeout)
GetScriptTimeout()

传回一个浮点数型态(float)来表示旧的暂停时间数值。

特殊事件
  如果他们已经被定义在脚本(script)里,EON将会呼叫以下的子程序。注意:JScript是有区分大小写能力(case sensitive)的程序。如果在以下的范例您使用JScript来撰写,您将必须拼写出子程序 "initialize", "shutdown"和 "eventProcessed"。

Initialize()

  当仿真程序启动时,Initialize()将马上被执行。注意:如果使用JScript,子函式必须拼写成initialize。

sub Initialize() 
specialCount = 0
end sub


当此仿真程序开始时,子函式将重新设定specialCount的数值。

 Shutdown()

当仿真程序关闭时,Shutdown()将马上被执行。

注意:如果使用JScript,子函式必须拼写成shutdown且eon必须以小写(lower-case)字母来写入。

sub Shutdown() 
EON.Trace("Hit/Miss" & (hit/misses) & "!")
end sub
EventsProcessed()

  有时候,一个Script节点的汇入事件 (in-events) 会比输出事件 (out-events) 频繁。而因为每一次汇入事件皆需产生新的运算,所以可以使用EventsProcessed()来取代此步骤。有On_in-event()的汇入事件会自动地设定它们eventIn字段的变量(variables),可设置一个旗子来表示那些值已经改变。

  假设有两个为SFVec3f型态的字段(p1和p2),且这些包含着两对象的(X,Y,Z)位置。此script运算出对象间的距离,但数据更新部份只有当一个新的框架被运算时才会执行。注意:如果使用JScript,子程序则必须拼写为eventsProcessed。

sub EventsProcessed() 
x=p1
y=p2
dSquared = (x(0)-y(0))^2+(x(1)-y(1))^2+(x(2)-y(2))^2
end sub

  当在准备一个屏幕框架时,EventsProcessed()将被执行。如果最后一个框架没有接收到任何汇入事件,EventsProcessed()将不会被执行。

功能节点之函数

 GetParentNode()

将此函数值传回至其父系节点。

set dad = aNode.GetParentNode() 

  藉由使用关键词的设定,此叙述将建立一个名为dad的对象变量。任何对象变量的改变将会影响其参照之父系节点。以下范例为增加其父系节点Z轴方位1单位:

sub On_Time() 

' Get the position from the parent

set ParentNode=This.GetParentNode()

set Pos=ParentNode.GetFieldByName("Position")

' Get its value

p=Pos.Value

' Increase the z value by 1

p(2)=p(2)+1

' Set new value of position

Pos.Value=p

end sub

在此范例中最重要的的是下面这行:

set ParentNode=This.GetParentNode() 

这个叙述将建立一个名为ParentNode的对象变量,它总是参照Script节点。

 GetFieldByName(SFString)

  此SFString函数将会回传至所指定的字段或一个script error。使用 VBScript On Error Resume Next叙述能处理任何错误。一个正常的处理将建立一个回传字段复本和任何影响的复本。

set position = aNode.GetFieldByName("translation") 

  这行设定参照aNode的位置字段。藉由使用关键设定,此叙述建立一个名为position的对象变量。对象的任何更改将会影响相关的参考字段。

GetIdOfName(SFString)

这个函数值会回传由字符串指定的ID 字段,如果找不到此字段会产生script error。

id = aNode.GetIdOfName("translation") 

这个叙述将指定aNode内的translation字段之ID数量。

GetField(SFInt32)

  这个函数将传回指定字段的参数,一个正常的值将建立一个复制的字段,任何改变只针对本机复本。

set position = aNode.GetField(id) 

  藉由使用关键词设定,建立一个名为位置 (position) 的对象变量,在这上面做的任何改变将影响参考字段。

GetFieldCount()

传回一个代表节点里的字段数字之整数值。

x = aNode.GetFieldCount() 

这个叙述指定aNode字段的数值为x。

单一函数值的字段

含单一函数值的字段 (例如SFBool数据型态的字段) ,您可使用以下所说明的功能。

Value
改变字段内数值

f.Value = TRUE 

这个叙述将设定一个名为f的数值为TRUE(真值)。

GetType()

这个函数将传回一个表示字段数据型态之整数值。

'Checks if SFBool 

If f.GetType() = 0 Then f.Value = TRUE

  这个叙述是用来确认f字段的布尔值(SFBool)并试图使它成为TRUE(真值)。以下的常数是EON事先定义好的数据型态。

Data type
数据型态
Predefined constant
资料代码

SFBool
0

SFColor
1

SFFloat
2

SFImage
3

SFInt32
4

SFNode
5

SFRotation
6

SFString
7

SFTime
8

SFVec3f
9

SFVec2f
10

GetName()

这个函数功能是传回一个字段的名称。

If f.GetName() = "Mass" Then f.Value = 100 

当f字段的名称是Mass时,指定f的值为100

MFNode字段的函数值

  所有的节点都有一个用来列示其子节点的字段。此字段的数据型态为MFNode。下列函数为Script节点中MFNode字段。

GetMFCount()

这个函数的传回值是一个整数用来呼应节点数量 (储存在Script节点的子字段)

x=Children.GetMFCount() 

当设定x为3时,表Script节点里有三个子字段。

GetMFElement(SFInt32) 

  从0开始编号的子系节点。如果一个节点含有三个子系节点,它们将以0,1和2来被编号。例如下列范例当x=1时,此函数值将传回至第一个子系节点。

aNode=Children.GetMFElement(x-1) 

一个任务将会产生回传节点的复制。任何可变物的差异将只会影响其复制节点。

set aNode=Children.GetMFElement(x-1) 

  藉由使用关键词的设定,此陈述将产生一个名为aNode的对象变量。任何在对象变量的改变将会影响其参考节点。

  在此范例中,如果将TRUE值以输入事件传送至子程序SetAllChildrenActive,那所有子系节点将会启动。如果送出的值为FALSE,那所有的子系节点将不会被启动。

' This procedure will activate/deactivate all child nodes 

sub On_SetAllChildrenActive

' Get no of children to this node

nrChildren=TreeChildren.GetMFCount()

' Set all children active

for i=0 to nrChildren-1

' Get a reference to child i

set child=TreeChildren.GetMFElement(i)

' Get propertyfield

set SetRunField=child.GetFieldByName("SetRun")

' Set SetRun to TRUE/FALSE

SetRunField.Value=activate

next

end sub

RemoveMFElement(SFInt32)

此函数将从MFNode字段移除指定的节点。

goodNodes.RemoveMFElement(x) 

此行列表从MFNode字段中移除名为goodNodes的x元素。

AddMFElement(SFNode)

这个函数将加入特定的节点到MFNode字段。

goodNodes.AddMFElement(aNode) 

此叙述将一个名为goodNodes的aNode加入至MFNode字段。

  此script的范例表示储存了Move1至Move10的所有节点,且这些节点在稍后的子程序SetActive中将被使用。SetActive接收到一个参数用来指定启动那一个 ”Move” 节点。使用此子程序来替代EON FindNode的动作,使用者每一次将更新必须更新的字段。

' This function executes once when a simulation starts 

' In this case:

' Remove all nodes in memory and fill with new ones

' EON.FindNode can always be used instead of putting

' nodes in a MFNode memory but this is more effective.

sub Initialize()

' Remove all stored nodes

nrOld=Store.GetMFCount()

for i=0 to nrOld

Store.RemoveMFElement(0)

next

' Find all nodes

' and put it in the memory of nodes

for i=0 to 10

set MoveNode=EON.FindNode("Move" & i)

Store.AddMFElement(MoveNode)

next

end sub

' Set node Nr to IsActive=TRUE

sub SetActive(Nr)

' Get a reference to node Nr

set MoveNode=Store.GetMFElement(Nr)

' Get propertyfield

set SetRun=MoveNode.GetFieldByName("SetRun")

' Set SetRun to TRUE

SetRun.Value=TRUE

end sub

SetMFElement(SFInt32, SFNode)

此函式是将取代所指定的节点。

goodNodes.SetMFElement , goodNodes.GetMFElement (x+1) 

此叙述是名为含x+1元素的goodNodes取代MFNode字段之x元素。

Access SFVec3f from JScript

为从JScript存取3D 浮点数型态向量(float vector)- SFVec3f,使用者须要转换数组。叙述如下:

ar arr = SFVec3fIn.Value.toArray(); 

指定数组部份程序为数据型态,此范例中我们将它附加至一字符串中。

SFStringOut.Value = str + arr[0];
(完)
可打印版本 | 文章评论 | 我来纠错

|网友评论

    笔名:

    内容:

        

    iPad售楼系统软件

    国内最好的全景漫游软件任我游

    iHouse售楼系统软件

    谁都可以轻松开发APP(HTML5APP)

    全景视频3D视频视景360

    HTML5移动平台iOS/Android解决方案

    强大的地图引擎ZoomMap

    环物浏览器Object360

    |热点关注

    关于我们 - 版权隐私 - 友情链接 - 广告服务 - 项目合作 - 网站地图 - 联系方式

    ©Copyright by 86CG.COM, 2006-2013. All rights reserved 京ICP备06059503号