1、模型描述
通过红色飞板,将输送机处的货物逐个传送到货架指定货位,货位由货位表指定。
2、模型布局
3、解决方案
3.1、载荷发生器
首先给载荷发生器创建自定义属性Loc,类型为表。
在载荷发生器的属性窗口中,找到自定义属性Loc,编辑此表,8行*3列,列名分别为rack(货架号)、bay(列号)、lvl(层号),对应货物上架存储的物理位置。每行代表一个载荷,每行值代表每个载荷将来要存放在货架上的位置。
接下来是对载荷生成器生成的每个载荷中,附带货架号、列号、层号信息。方法是在载荷的OnLoadCreated事件中,编写相应代码如下:
function LoadCreator1_OnLoadCreated( sender : Demo3D.Visuals.LoadCreatorVisual, load : Demo3D.Visuals.Visual )
{
var table:Table=sender.Loc.Table; //定义表,取值为载荷生成器的Loc自定义属性,注意引用表属性时,要额外加 .Table 后缀
var rowcount:int=table.Rows.Count; //定义表的总行数
var seq:int=sender.SequenceNumber; //定义载荷的生成序号,即载荷生成器创建的第几个载荷
//为当前载荷创建rack、col、lvl 属性,其值为表Loc 的相应列值
if(!load.HasCustomProperty(“rack”)){
load.AddSimpleProperty(“rack”,table.Rows[seq][“rack”],”rack”);
}
if(!load.HasCustomProperty(“col”)){
load.AddSimpleProperty(“col”,table.Rows[seq][“col”],”rack”);
}
if(!load.HasCustomProperty(“lvl”)){
load.AddSimpleProperty(“lvl”,table.Rows[seq][“lvl”],”rack”);
}
//如果当前载荷序号超过了表的总行数,则禁止载荷生成器生成载荷
if(seq==rowcount-1){
sender.ReleaseEnabled=False;
}
}
在载荷生成器的OnReset事件中启用生成载荷
function LoadCreator1_OnReset( sender : Demo3D.Visuals.LoadCreatorVisual )
{
sender.ReleaseEnabled=True;
}
3.2、飞板
3.2.1、飞板初始化
在飞板的OnReset事件中编写代码
//自定义移动速度属性
if ( ! sender.HasProperty(“LinearSpeed”) )
{
sender.AddSimpleProperty(“LinearSpeed”, new SpeedProfile(1, 0.5, 0.5),””);
}
//自定义旋转速度属性
if ( ! sender.HasProperty(“RotationSpeed”) )
{
sender.AddSimpleProperty(“RotationSpeed”, new AngularSpeedProfile(90,45, 45), “”);
}
sender.WorldLocation = vector(0, 0, 0); //设置飞板初始位置在世界坐标系原点
sender.WorldRotationY = 0; //设置飞板的初始旋转轴
3.2.2、设置飞板监听光眼
3.2.3、飞板的 OnMessage 事件
编写代码如下:
function flyPad_OnMessage( sender : Demo3D.Visuals.BoxVisual, message : Demo3D.Visuals.ScriptingObject )
{
//监听到的事件如果不是光眼 PE1的 OnBlocked 事件,则退出本程序,不作任何处理
if(!(message[“MessageType”]==”OnBlocked” && message.MessageSender.Name==”PE1″)){
return;
}
//否则,进行如下处理
var load:Visual=message[“load”];
var pe:PhotoEys=message[“MessageSender”];
var conv:Demo3D.Visuals.StraightRollerConveyor= pe.Parent;
conv.MotorOff();//关闭输送机马达
//飞板原地升降,高度与输送机高度相同
var targetLoc:Vector3=sender.WorldLocation;
targetLoc.Y=conv.Height;
sender.MoveTo(targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//飞板原地旋转,X轴向与输送机X轴向相对
var targetRot:Vector3=Degrees(conv.WorldRotation);
sender.TurnTo(Axis.Y,180+targetRot.Y,sender.RotationSpeed);
sender.WaitForMove();
//飞板移动到输送机出口处
sender.SetInitialPosition();
var convStartLoc:Vector3=sender.TransformFromWorld(conv.WorldLocation);
var convEndLoc:Vector3=new Vector3();
convEndLoc.X=convStartLoc.X-conv.Length-sender.Width/2.0;
convEndLoc.Z=convStartLoc.Z;
sender.MoveTo(sender,convEndLoc,sender.LinearSpeed);
sender.WaitForMove();
//叉齿伸出接货
var extender:Visual=sender.FindChild(“extender”);
extender.TranslateLocalX(load.Width+0.2,1);
extender.WaitForMove();
//货物绑定到叉齿,叉齿回缩
load.Stick(extender);
extender.TranslateLocalX(-load.Width-0.2,1);
extender.WaitForMove();
var rackIdx:int=load.rack-1;//定义货架排号,取值为货物附带的rack属性值
var shelfIdx:int=load.lvl-1;//定义货架层号,取值为货物附带的lvl属性值
var bayIdx:int=load.col-1;//定义货架格号,取值为货物附带的col属性值
var rack1:Visual=doc.FindVisualByName(“Rack1”);//货架组件
var racks:RackVisual[]=rack1.FindType(RackVisual);//定义一个数组,其素对应为货架组件中的单排货架
racks.Sort(new VisualDistanceComparer(rack1.WorldLocation));//货架数组排序,即racks[0]为第一排货架,rack[1]为第2排货架,等等
var targetRack:RackVisual=racks[rackIdx];//货物待上架的目标货架
var shelves:ShelfVisual[]=targetRack.FindType(ShelfVisual);//定义一个数组,其素为目标货架的各搁板
shelves.Sort(new VisualDistanceComparer(targetRack.WorldLocation));//搁板数组排序,即shelves[0]为第一层搁板,shelves[1]为第2层搁板,等等
var targetShelf:ShelfVisual=shelves[shelfIdx];//目标搁板
targetRot=Degrees(targetShelf.WorldRotation);//目标搁板的角度
//奇偶数排货架,其货架前后端位置正好相反
if(rackIdx % 2==0){ //奇数排货架
//飞板原地旋转
sender.TurnTo(Axis.Y,targetRot.Y,sender.RotationSpeed);//飞板原地旋转,角度与目标搁板方向相同
sender.WaitForMove();
//飞板水平移动到目标搁板前端入口处
sender.SetInitialPosition();
targetLoc=targetShelf.WorldLocation;//目标搁板世界坐标
targetLoc=sender.TransformFromWorld(targetLoc);//将目标搁板世界坐标转换为相对坐标
//目标位置微调
targetLoc.X -=sender.Width/2.0;
targetLoc.Y =0;
targetLoc.Z -=sender.Depth/2.0;
//飞板水平移动
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//目标货格位置
var binLoc:BinLocation=new BinLocation();
binLoc.Bay=bayIdx;
binLoc.Bin=0;
binLoc.Index=0;
//目标货格坐标处理
sender.SetInitialPosition();
targetLoc=targetShelf.GetNextStoragePosition(binLoc);//获取目标货格相对目标搁板的的坐标(注意是相对坐标)
targetLoc=targetShelf.TransformToWorld(targetLoc);//目标位置的相对坐标转换为世界坐标
targetLoc=sender.TransformFromWorld(targetLoc);//目标位置的世界坐标再转换为相对飞板的相对坐标
var targetBinLocY:Double=targetLoc.Y;//保存目标货格的Y坐标,用于定位下一步中飞板原地升降的高度
//目标位置微调
targetLoc.Y =0;
targetLoc.Z =0;
//飞板平移动到目标货格附近
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//飞板原地转90°
sender.SetInitialPosition();
sender.TurnTo(sender,Axis.Y,270,sender.RotationSpeed);
sender.WaitForMove();
//飞板原地升降到目标货格高度
sender.SetInitialPosition();
targetLoc.X=0;
targetLoc.Y=targetBinLocY;
targetLoc.Z=0;
sender.SetInitialPosition();
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//叉齿伸出放货
sender.SetInitialPosition();
extender.TranslateLocalX(load.Width+targetShelf.BayDepth/2.0,1);
extender.WaitForMove();
//放货,将货物与目标搁板绑定
load.Stick(targetShelf);
//叉齿缩回
sender.SetInitialPosition();
extender.TranslateLocalX(-(load.Width+targetShelf.BayDepth/2.0),1);
extender.WaitForMove();
//飞板移动到目标搁板入口处
sender.SetInitialPosition();
targetLoc=targetShelf.WorldLocation;
targetLoc=sender.TransformFromWorld(targetLoc);
targetLoc.X -=sender.Width/2.0;
targetLoc.Z +=sender.Depth/2.0;
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
}
else{ //偶数排货架
//飞板原地旋转
sender.TurnTo(Axis.Y,180+targetRot.Y,sender.RotationSpeed);//飞板原地旋转,角度与目标搁板方向相同
sender.WaitForMove();
//飞板水平移动到目标搁板后端入口处
sender.SetInitialPosition();
targetLoc=targetShelf.WorldLocation;//目标搁板世界坐标
targetLoc=sender.TransformFromWorld(targetLoc);//将目标搁板世界坐标转换为相对坐标
//目标位置微调
targetLoc.X -=(targetShelf.OverallLength+sender.Width/2.0);
targetLoc.Y =0;
targetLoc.Z +=sender.Depth/2.0;
//飞板水平移动
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//目标货格位置
var binLoc:BinLocation=new BinLocation();
binLoc.Bay=bayIdx;
binLoc.Bin=0;
binLoc.Index=0;
//目标货格坐标处理
sender.SetInitialPosition();
targetLoc=targetShelf.GetNextStoragePosition(binLoc);//获取目标货格相对目标搁板的的坐标(注意是相对坐标)
targetLoc=targetShelf.TransformToWorld(targetLoc);//目标位置的相对坐标转换为世界坐标
targetLoc=sender.TransformFromWorld(targetLoc);//目标位置的世界坐标再转换为相对飞板的相对坐标
var targetBinLocY:Double=targetLoc.Y;//保存目标货格的Y坐标,用于定位下一步中飞板原地升降的高度
//目标位置微调
targetLoc.Y =0;
targetLoc.Z =0;
//飞板平移动到目标货格附近
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//飞板原地转90°
sender.SetInitialPosition();
sender.TurnTo(sender,Axis.Y,90,sender.RotationSpeed);
sender.WaitForMove();
//飞板原地升降到目标货格高度
sender.SetInitialPosition();
targetLoc.X=0;
targetLoc.Y=targetBinLocY;
targetLoc.Z=0;
sender.SetInitialPosition();
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
//叉齿伸出放货
sender.SetInitialPosition();
extender.TranslateLocalX(load.Width+targetShelf.BayDepth/2.0,1);
extender.WaitForMove();
//放货,将货物与目标搁板绑定
load.Stick(targetShelf);
//叉齿缩回
sender.SetInitialPosition();
extender.TranslateLocalX(-(load.Width+targetShelf.BayDepth/2.0),1);
extender.WaitForMove();
//飞板水平移动到目标搁板后端入口处
sender.SetInitialPosition();
targetLoc=targetShelf.WorldLocation;//目标搁板世界坐标
targetLoc=sender.TransformFromWorld(targetLoc);//将目标搁板世界坐标转换为相对坐标
//目标位置微调
targetLoc.X -=sender.Depth/2.0;
targetLoc.Z -=(targetShelf.OverallLength+sender.Width/2.0);
//飞板水平移动
sender.MoveTo(sender,targetLoc,sender.LinearSpeed);
sender.WaitForMove();
}
conv.MotorOn();//飞板完成传输任务后,开启输送机马达,使得输送机上的下一个载荷移动,又一次触发光眼的 OnBlocked 事件。
}
4、最终效果
5、学习小结
5.1、利用载荷发生器的SequenceNumber属性,作为行号去读取一个表的行列值;
5.2、用代码对载荷发生器创建的载荷,创建待上架位置的自定义属性;
5.3、用代码开启某对象的监听功能,设置两个对象之间监听和被监听的关系;
5.4、对象的 OnMessage 事件,以及参数message的运用,注意参数 message 的数据类型是字典,其主要键名有MessageSender、MessageType;
5.5、利用飞板的 OnMessage 事件,来处理飞板监听到的光眼封堵事件;
5.6、对象移动函数 MoveTo()、旋转函数 TurnTo() 的应用,特别要注意参考坐标系的应用;
5.7、对象旋转时,应注意单位是角度还是弧度,以及角度单位的转换;
5.8、参考坐标系为相对坐标时,SetInitialPosition() 函数的应用;
5.9、注意货架组中,奇数排货架和偶数排货架的前端/后端位置正好相反;
5.10、获取货架的货格位置的相应坐标函数 Shelf.GetNextStoragePosition(binLoc) 的应用;
5.11、货架对象的层级关系:货架对象 > 货架组 RackVisual[ ]> 搁板组 ShelfVisual[ ]> 货格组;
5.12、Sort()函数对货架数组 RackVisual[ ]、搁板数组 ShelfVisual[ ] 中的素按某种规则进行排序。
2024最新激活全家桶教程,稳定运行到2099年,请移步至置顶文章:https://sigusoft.com/99576.html
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。 文章由激活谷谷主-小谷整理,转载请注明出处:https://sigusoft.com/148366.html